Source Code
Latest 25 from a total of 67 transactions
| Transaction Hash |
|
Block
|
From
|
To
|
|||||
|---|---|---|---|---|---|---|---|---|---|
| Stake Tier FS To... | 49364625 | 113 days ago | IN | 0 S | 0.01310424 | ||||
| Unstake Tier FS ... | 49364177 | 113 days ago | IN | 0 S | 0.00448514 | ||||
| Stake Tier FS To... | 32989867 | 230 days ago | IN | 0 S | 0.01161657 | ||||
| Update Current S... | 27546631 | 253 days ago | IN | 0 S | 0.00609972 | ||||
| Stake Tier FS To... | 25884391 | 260 days ago | IN | 0 S | 0.01310353 | ||||
| Unstake Tier FS ... | 17210354 | 301 days ago | IN | 0 S | 0.00459614 | ||||
| Unstake Tier FS ... | 17155220 | 301 days ago | IN | 0 S | 0.0053863 | ||||
| Unstake Tier FS ... | 16988783 | 302 days ago | IN | 0 S | 0.00459614 | ||||
| Update Current S... | 16306473 | 305 days ago | IN | 0 S | 0.00540351 | ||||
| Stake Tier FS To... | 15871877 | 307 days ago | IN | 0 S | 0.01161597 | ||||
| Unstake Tier FS ... | 15675316 | 307 days ago | IN | 0 S | 0.00538532 | ||||
| Update Current S... | 13838889 | 317 days ago | IN | 0 S | 0.00540351 | ||||
| Stake Tier FS To... | 13836973 | 317 days ago | IN | 0 S | 0.01161597 | ||||
| Unstake Tier FS ... | 11447016 | 328 days ago | IN | 0 S | 0.0046963 | ||||
| Stake Tier FS To... | 11443582 | 328 days ago | IN | 0 S | 0.0122087 | ||||
| Stake Tier FS To... | 9163348 | 338 days ago | IN | 0 S | 0.01277754 | ||||
| Stake Tier FS To... | 8924811 | 339 days ago | IN | 0 S | 0.01343206 | ||||
| Unstake Tier FS ... | 8918081 | 339 days ago | IN | 0 S | 0.00538532 | ||||
| Stake Tier FS To... | 8663190 | 341 days ago | IN | 0 S | 0.01343206 | ||||
| Stake Tier FS To... | 8653039 | 341 days ago | IN | 0 S | 0.01342962 | ||||
| Stake Tier FS To... | 8133055 | 344 days ago | IN | 0 S | 0.01277754 | ||||
| Unstake Tier FS ... | 7519272 | 348 days ago | IN | 0 S | 0.00512732 | ||||
| Unstake Tier FS ... | 7359358 | 349 days ago | IN | 0 S | 0.00459614 | ||||
| Unstake Tier FS ... | 5851806 | 361 days ago | IN | 0 S | 0.00512732 | ||||
| Unstake Tier FS ... | 5571288 | 364 days ago | IN | 0 S | 0.00512732 |
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Cross-Chain Transactions
Loading...
Loading
Contract Name:
StakerTierFSonic
Compiler Version
v0.8.18+commit.87f61d96
Contract Source Code (Solidity)
/**
*Submitted for verification at SonicScan.org on 2024-12-16
*/
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.10;
/**
* @dev Provides information about the current execution context, including the
* sender of the transaction and its data. While these are generally available
* via msg.sender and msg.data, they should not be accessed in such a direct
* manner, since when dealing with meta-transactions the account sending and
* paying for execution may not be the actual sender (as far as an application
* is concerned).
*
* This contract is only required for intermediate, library-like contracts.
*/
abstract contract Context {
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
}
// CAUTION
// This version of SafeMath should only be used with Solidity 0.8 or later,
// because it relies on the compiler's built in overflow checks.
/**
* @dev Wrappers over Solidity's arithmetic operations.
*
* NOTE: `SafeMath` is no longer needed starting with Solidity 0.8. The compiler
* now has built in overflow checking.
*/
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) {
unchecked {
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) {
unchecked {
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) {
unchecked {
// 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) {
unchecked {
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) {
unchecked {
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) {
return a + b;
}
/**
* @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) {
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) {
return a * b;
}
/**
* @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.
*
* Requirements:
*
* - The divisor cannot be zero.
*/
function div(uint256 a, uint256 b) internal pure returns (uint256) {
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) {
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) {
unchecked {
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.
*
* 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) {
unchecked {
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) {
unchecked {
require(b > 0, errorMessage);
return a % b;
}
}
}
/**
* @dev Interface of the ERC165 standard, as defined in the
* https://eips.ethereum.org/EIPS/eip-165[EIP].
*
* Implementers can declare support of contract interfaces, which can then be
* queried by others ({ERC165Checker}).
*
* For an implementation, see {ERC165}.
*/
interface IERC165 {
/**
* @dev Returns true if this contract implements the interface defined by
* `interfaceId`. See the corresponding
* https://eips.ethereum.org/EIPS/eip-165#how-interfaces-are-identified[EIP section]
* to learn more about how these ids are created.
*
* This function call must use less than 30 000 gas.
*/
function supportsInterface(bytes4 interfaceId) external view returns (bool);
}
/**
* @dev Implementation of the {IERC165} interface.
*
* Contracts that want to implement ERC165 should inherit from this contract and override {supportsInterface} to check
* for the additional interface id that will be supported. For example:
*
* ```solidity
* function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
* return interfaceId == type(MyInterface).interfaceId || super.supportsInterface(interfaceId);
* }
* ```
*
* Alternatively, {ERC165Storage} provides an easier to use but more expensive implementation.
*/
abstract contract ERC165 is IERC165 {
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(
bytes4 interfaceId
) public view virtual override returns (bool) {
return interfaceId == type(IERC165).interfaceId;
}
}
/**
* @dev String operations.
*/
library Strings {
bytes16 private constant _HEX_SYMBOLS = "0123456789abcdef";
/**
* @dev Converts a `uint256` to its ASCII `string` decimal representation.
*/
function toString(uint256 value) internal pure returns (string memory) {
// Inspired by OraclizeAPI's implementation - MIT licence
// https://github.com/oraclize/ethereum-api/blob/b42146b063c7d6ee1358846c198246239e9360e8/oraclizeAPI_0.4.25.sol
if (value == 0) {
return "0";
}
uint256 temp = value;
uint256 digits;
while (temp != 0) {
digits++;
temp /= 10;
}
bytes memory buffer = new bytes(digits);
while (value != 0) {
digits -= 1;
buffer[digits] = bytes1(uint8(48 + uint256(value % 10)));
value /= 10;
}
return string(buffer);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation.
*/
function toHexString(uint256 value) internal pure returns (string memory) {
if (value == 0) {
return "0x00";
}
uint256 temp = value;
uint256 length = 0;
while (temp != 0) {
length++;
temp >>= 8;
}
return toHexString(value, length);
}
/**
* @dev Converts a `uint256` to its ASCII `string` hexadecimal representation with fixed length.
*/
function toHexString(
uint256 value,
uint256 length
) internal pure returns (string memory) {
bytes memory buffer = new bytes(2 * length + 2);
buffer[0] = "0";
buffer[1] = "x";
for (uint256 i = 2 * length + 1; i > 1; --i) {
buffer[i] = _HEX_SYMBOLS[value & 0xf];
value >>= 4;
}
require(value == 0, "Strings: hex length insufficient");
return string(buffer);
}
}
/**
* @dev Collection of functions related to the address type
*/
library Address {
/**
* @dev Returns true if `account` is a contract.
*
* [IMPORTANT]
* ====
* It is unsafe to assume that an address for which this function returns
* false is an externally-owned account (EOA) and not a contract.
*
* Among others, `isContract` will return false for the following
* types of addresses:
*
* - an externally-owned account
* - a contract in construction
* - an address where a contract will be created
* - an address where a contract lived, but was destroyed
* ====
*/
function isContract(address account) internal view returns (bool) {
// This method relies on extcodesize, which returns 0 for contracts in
// construction, since the code is only stored at the end of the
// constructor execution.
uint256 size;
assembly {
size := extcodesize(account)
}
return size > 0;
}
/**
* @dev Replacement for Solidity's `transfer`: sends `amount` wei to
* `recipient`, forwarding all available gas and reverting on errors.
*
* https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
* of certain opcodes, possibly making contracts go over the 2300 gas limit
* imposed by `transfer`, making them unable to receive funds via
* `transfer`. {sendValue} removes this limitation.
*
* https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].
*
* IMPORTANT: because control is transferred to `recipient`, care must be
* taken to not create reentrancy vulnerabilities. Consider using
* {ReentrancyGuard} or the
* https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
*/
function sendValue(address payable recipient, uint256 amount) internal {
require(
address(this).balance >= amount,
"Address: insufficient balance"
);
(bool success, ) = recipient.call{value: amount}("");
require(
success,
"Address: unable to send value, recipient may have reverted"
);
}
/**
* @dev Performs a Solidity function call using a low level `call`. A
* plain `call` is an unsafe replacement for a function call: use this
* function instead.
*
* If `target` reverts with a revert reason, it is bubbled up by this
* function (like regular Solidity function calls).
*
* Returns the raw returned data. To convert to the expected return value,
* use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
*
* Requirements:
*
* - `target` must be a contract.
* - calling `target` with `data` must not revert.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data
) internal returns (bytes memory) {
return functionCall(target, data, "Address: low-level call failed");
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
* `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but also transferring `value` wei to `target`.
*
* Requirements:
*
* - the calling contract must have an ETH balance of at least `value`.
* - the called Solidity function must be `payable`.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value
) internal returns (bytes memory) {
return
functionCallWithValue(
target,
data,
value,
"Address: low-level call with value failed"
);
}
/**
* @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
* with `errorMessage` as a fallback revert reason when `target` reverts.
*
* _Available since v3.1._
*/
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(
address(this).balance >= value,
"Address: insufficient balance for call"
);
require(isContract(target), "Address: call to non-contract");
(bool success, bytes memory returndata) = target.call{value: value}(
data
);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data
) internal view returns (bytes memory) {
return
functionStaticCall(
target,
data,
"Address: low-level static call failed"
);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a static call.
*
* _Available since v3.3._
*/
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
require(isContract(target), "Address: static call to non-contract");
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(
address target,
bytes memory data
) internal returns (bytes memory) {
return
functionDelegateCall(
target,
data,
"Address: low-level delegate call failed"
);
}
/**
* @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
* but performing a delegate call.
*
* _Available since v3.4._
*/
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
require(isContract(target), "Address: delegate call to non-contract");
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResult(success, returndata, errorMessage);
}
/**
* @dev Tool to verifies that a low level call was successful, and revert if it wasn't, either by bubbling the
* revert reason using the provided one.
*
* _Available since v4.3._
*/
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
// Look for revert reason and bubble it up if present
if (returndata.length > 0) {
// The easiest way to bubble the revert reason is using memory via assembly
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}
}
/**
* @dev External interface of AccessControl declared to support ERC165 detection.
*/
interface IAccessControl {
function hasRole(
bytes32 role,
address account
) external view returns (bool);
function getRoleAdmin(bytes32 role) external view returns (bytes32);
function grantRole(bytes32 role, address account) external;
function revokeRole(bytes32 role, address account) external;
function renounceRole(bytes32 role, address account) external;
}
/**
* @dev Contract module that allows children to implement role-based access
* control mechanisms. This is a lightweight version that doesn't allow enumerating role
* members except through off-chain means by accessing the contract event logs. Some
* applications may benefit from on-chain enumerability, for those cases see
* {AccessControlEnumerable}.
*
* Roles are referred to by their `bytes32` identifier. These should be exposed
* in the external API and be unique. The best way to achieve this is by
* using `public constant` hash digests:
*
* ```
* bytes32 public constant MY_ROLE = keccak256("MY_ROLE");
* ```
*
* Roles can be used to represent a set of permissions. To restrict access to a
* function call, use {hasRole}:
*
* ```
* function foo() public {
* require(hasRole(MY_ROLE, msg.sender));
* ...
* }
* ```
*
* Roles can be granted and revoked dynamically via the {grantRole} and
* {revokeRole} functions. Each role has an associated admin role, and only
* accounts that have a role's admin role can call {grantRole} and {revokeRole}.
*
* By default, the admin role for all roles is `DEFAULT_ADMIN_ROLE`, which means
* that only accounts with this role will be able to grant or revoke other
* roles. More complex role relationships can be created by using
* {_setRoleAdmin}.
*
* WARNING: The `DEFAULT_ADMIN_ROLE` is also its own admin: it has permission to
* grant and revoke this role. Extra precautions should be taken to secure
* accounts that have been granted it.
*/
abstract contract AccessControl is Context, IAccessControl, ERC165 {
struct RoleData {
mapping(address => bool) members;
bytes32 adminRole;
}
mapping(bytes32 => RoleData) private _roles;
bytes32 public constant DEFAULT_ADMIN_ROLE = 0x00;
/**
* @dev Emitted when `newAdminRole` is set as ``role``'s admin role, replacing `previousAdminRole`
*
* `DEFAULT_ADMIN_ROLE` is the starting admin for all roles, despite
* {RoleAdminChanged} not being emitted signaling this.
*
* _Available since v3.1._
*/
event RoleAdminChanged(
bytes32 indexed role,
bytes32 indexed previousAdminRole,
bytes32 indexed newAdminRole
);
/**
* @dev Emitted when `account` is granted `role`.
*
* `sender` is the account that originated the contract call, an admin role
* bearer except when using {_setupRole}.
*/
event RoleGranted(
bytes32 indexed role,
address indexed account,
address indexed sender
);
/**
* @dev Emitted when `account` is revoked `role`.
*
* `sender` is the account that originated the contract call:
* - if using `revokeRole`, it is the admin role bearer
* - if using `renounceRole`, it is the role bearer (i.e. `account`)
*/
event RoleRevoked(
bytes32 indexed role,
address indexed account,
address indexed sender
);
/**
* @dev Modifier that checks that an account has a specific role. Reverts
* with a standardized message including the required role.
*
* The format of the revert reason is given by the following regular expression:
*
* /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
*
* _Available since v4.1._
*/
modifier onlyRole(bytes32 role) {
_checkRole(role, _msgSender());
_;
}
modifier isAdmin() {
require(
hasRole(DEFAULT_ADMIN_ROLE, _msgSender()),
"Account is not in the admin list"
);
_;
}
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(
bytes4 interfaceId
) public view virtual override returns (bool) {
return
interfaceId == type(IAccessControl).interfaceId ||
super.supportsInterface(interfaceId);
}
/**
* @dev Returns `true` if `account` has been granted `role`.
*/
function hasRole(
bytes32 role,
address account
) public view override returns (bool) {
return _roles[role].members[account];
}
/**
* @dev Revert with a standard message if `account` is missing `role`.
*
* The format of the revert reason is given by the following regular expression:
*
* /^AccessControl: account (0x[0-9a-f]{40}) is missing role (0x[0-9a-f]{64})$/
*/
function _checkRole(bytes32 role, address account) internal view {
if (!hasRole(role, account)) {
revert(
string(
abi.encodePacked(
"AccessControl: account ",
Strings.toHexString(uint160(account), 20),
" is missing role ",
Strings.toHexString(uint256(role), 32)
)
)
);
}
}
/**
* @dev Returns the admin role that controls `role`. See {grantRole} and
* {revokeRole}.
*
* To change a role's admin, use {_setRoleAdmin}.
*/
function getRoleAdmin(bytes32 role) public view override returns (bytes32) {
return _roles[role].adminRole;
}
/**
* @dev Grants `role` to `account`.
*
* If `account` had not been already granted `role`, emits a {RoleGranted}
* event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function grantRole(
bytes32 role,
address account
) public virtual override onlyRole(getRoleAdmin(role)) {
_grantRole(role, account);
}
/**
* @dev Revokes `role` from `account`.
*
* If `account` had been granted `role`, emits a {RoleRevoked} event.
*
* Requirements:
*
* - the caller must have ``role``'s admin role.
*/
function revokeRole(
bytes32 role,
address account
) public virtual override onlyRole(getRoleAdmin(role)) {
_revokeRole(role, account);
}
/**
* @dev Revokes `role` from the calling account.
*
* Roles are often managed via {grantRole} and {revokeRole}: this function's
* purpose is to provide a mechanism for accounts to lose their privileges
* if they are compromised (such as when a trusted device is misplaced).
*
* If the calling account had been granted `role`, emits a {RoleRevoked}
* event.
*
* Requirements:
*
* - the caller must be `account`.
*/
function renounceRole(
bytes32 role,
address account
) public virtual override {
require(
account == _msgSender(),
"AccessControl: can only renounce roles for self"
);
_revokeRole(role, account);
}
/**
* @dev Grants `role` to `account`.
*
* If `account` had not been already granted `role`, emits a {RoleGranted}
* event. Note that unlike {grantRole}, this function doesn't perform any
* checks on the calling account.
*
* [WARNING]
* ====
* This function should only be called from the constructor when setting
* up the initial roles for the system.
*
* Using this function in any other way is effectively circumventing the admin
* system imposed by {AccessControl}.
* ====
*/
function _setupRole(bytes32 role, address account) internal virtual {
_grantRole(role, account);
}
/**
* @dev Sets `adminRole` as ``role``'s admin role.
*
* Emits a {RoleAdminChanged} event.
*/
function _setRoleAdmin(bytes32 role, bytes32 adminRole) internal virtual {
bytes32 previousAdminRole = getRoleAdmin(role);
_roles[role].adminRole = adminRole;
emit RoleAdminChanged(role, previousAdminRole, adminRole);
}
function _grantRole(bytes32 role, address account) private {
if (!hasRole(role, account)) {
_roles[role].members[account] = true;
emit RoleGranted(role, account, _msgSender());
}
}
function _revokeRole(bytes32 role, address account) private {
if (hasRole(role, account)) {
_roles[role].members[account] = false;
emit RoleRevoked(role, account, _msgSender());
}
}
}
/**
* @dev Required interface of an ERC1155 compliant contract, as defined in the
* https://eips.ethereum.org/EIPS/eip-1155[EIP].
*
* _Available since v3.1._
*/
interface IERC1155 is IERC165 {
/**
* @dev Emitted when `value` tokens of token type `id` are transferred from `from` to `to` by `operator`.
*/
event TransferSingle(
address indexed operator,
address indexed from,
address indexed to,
uint256 id,
uint256 value
);
/**
* @dev Equivalent to multiple {TransferSingle} events, where `operator`, `from` and `to` are the same for all
* transfers.
*/
event TransferBatch(
address indexed operator,
address indexed from,
address indexed to,
uint256[] ids,
uint256[] values
);
/**
* @dev Emitted when `account` grants or revokes permission to `operator` to transfer their tokens, according to
* `approved`.
*/
event ApprovalForAll(
address indexed account,
address indexed operator,
bool approved
);
/**
* @dev Emitted when the URI for token type `id` changes to `value`, if it is a non-programmatic URI.
*
* If an {URI} event was emitted for `id`, the standard
* https://eips.ethereum.org/EIPS/eip-1155#metadata-extensions[guarantees] that `value` will equal the value
* returned by {IERC1155MetadataURI-uri}.
*/
event URI(string value, uint256 indexed id);
/**
* @dev Returns the amount of tokens of token type `id` owned by `account`.
*
* Requirements:
*
* - `account` cannot be the zero address.
*/
function balanceOf(
address account,
uint256 id
) external view returns (uint256);
/**
* @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {balanceOf}.
*
* Requirements:
*
* - `accounts` and `ids` must have the same length.
*/
function balanceOfBatch(
address[] calldata accounts,
uint256[] calldata ids
) external view returns (uint256[] memory);
/**
* @dev Grants or revokes permission to `operator` to transfer the caller's tokens, according to `approved`,
*
* Emits an {ApprovalForAll} event.
*
* Requirements:
*
* - `operator` cannot be the caller.
*/
function setApprovalForAll(address operator, bool approved) external;
/**
* @dev Returns true if `operator` is approved to transfer ``account``'s tokens.
*
* See {setApprovalForAll}.
*/
function isApprovedForAll(
address account,
address operator
) external view returns (bool);
/**
* @dev Transfers `amount` tokens of token type `id` from `from` to `to`.
*
* Emits a {TransferSingle} event.
*
* Requirements:
*
* - `to` cannot be the zero address.
* - If the caller is not `from`, it must be have been approved to spend ``from``'s tokens via {setApprovalForAll}.
* - `from` must have a balance of tokens of type `id` of at least `amount`.
* - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155Received} and return the
* acceptance magic value.
*/
function safeTransferFrom(
address from,
address to,
uint256 id,
uint256 amount,
bytes calldata data
) external;
/**
* @dev xref:ROOT:erc1155.adoc#batch-operations[Batched] version of {safeTransferFrom}.
*
* Emits a {TransferBatch} event.
*
* Requirements:
*
* - `ids` and `amounts` must have the same length.
* - If `to` refers to a smart contract, it must implement {IERC1155Receiver-onERC1155BatchReceived} and return the
* acceptance magic value.
*/
function safeBatchTransferFrom(
address from,
address to,
uint256[] calldata ids,
uint256[] calldata amounts,
bytes calldata data
) external;
function mint(uint256 id, address receiver) external;
}
/**
* @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);
function mintToken(address account, uint256 amount) external;
/**
* @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
);
/**
* @dev Destroys `amount` tokens from the caller.
*
* See {ERC20-_burn}.
*/
function burn(uint256 amount) external;
/**
* @dev Destroys `amount` tokens from `account`, deducting from the caller's
* allowance.
*
* See {ERC20-_burn} and {ERC20-allowance}.
*
* Requirements:
*
* - the caller must have allowance for ``accounts``'s tokens of at least
* `amount`.
*/
function burnFrom(address account, uint256 amount) external;
}
/**
* @dev _Available since v3.1._
*/
interface IERC1155Receiver is IERC165 {
/**
@dev Handles the receipt of a single ERC1155 token type. This function is
called at the end of a `safeTransferFrom` after the balance has been updated.
To accept the transfer, this must return
`bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))`
(i.e. 0xf23a6e61, or its own function selector).
@param operator The address which initiated the transfer (i.e. msg.sender)
@param from The address which previously owned the token
@param id The ID of the token being transferred
@param value The amount of tokens being transferred
@param data Additional data with no specified format
@return `bytes4(keccak256("onERC1155Received(address,address,uint256,uint256,bytes)"))` if transfer is allowed
*/
function onERC1155Received(
address operator,
address from,
uint256 id,
uint256 value,
bytes calldata data
) external returns (bytes4);
/**
@dev Handles the receipt of a multiple ERC1155 token types. This function
is called at the end of a `safeBatchTransferFrom` after the balances have
been updated. To accept the transfer(s), this must return
`bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))`
(i.e. 0xbc197c81, or its own function selector).
@param operator The address which initiated the batch transfer (i.e. msg.sender)
@param from The address which previously owned the token
@param ids An array containing ids of each token being transferred (order and length must match values array)
@param values An array containing amounts of each token being transferred (order and length must match ids array)
@param data Additional data with no specified format
@return `bytes4(keccak256("onERC1155BatchReceived(address,address,uint256[],uint256[],bytes)"))` if transfer is allowed
*/
function onERC1155BatchReceived(
address operator,
address from,
uint256[] calldata ids,
uint256[] calldata values,
bytes calldata data
) external returns (bytes4);
}
/**
* @dev _Available since v3.1._
*/
abstract contract ERC1155Receiver is ERC165, IERC1155Receiver {
/**
* @dev See {IERC165-supportsInterface}.
*/
function supportsInterface(
bytes4 interfaceId
) public view virtual override(ERC165, IERC165) returns (bool) {
return
interfaceId == type(IERC1155Receiver).interfaceId ||
super.supportsInterface(interfaceId);
}
}
/**
* @dev _Available since v3.1._
*/
contract ERC1155Holder is ERC1155Receiver {
function onERC1155Received(
address,
address,
uint256,
uint256,
bytes memory
) public virtual override returns (bytes4) {
return this.onERC1155Received.selector;
}
function onERC1155BatchReceived(
address,
address,
uint256[] memory,
uint256[] memory,
bytes memory
) public virtual override returns (bytes4) {
return this.onERC1155BatchReceived.selector;
}
}
/**
* @dev
* Interface to access the TierFactory FSonic
**/
interface ITierFactoryFSonic {
/**
* @dev
* Returns the balance of the number of NFTs based on the NFTId
**/
function balanceOf(
address _owner,
uint256 _id
) external view returns (uint256);
/**
* @dev
* Returns the balance of a list of addresses
**/
function balanceOfBatch(
address[] calldata _owners,
uint256[] calldata _ids
) external view returns (uint256[] memory);
/**
* @dev
* Mint the NFT
**/
function mint(
address _to,
uint256 _id,
uint256 _quantity,
bytes calldata _data
) external;
/**
* @dev
* Check if the NFT is mintable
**/
function isMintable(uint256 _id) external returns (bool);
/**
* @dev
* Transfer the NFT _from _to
**/
function safeTransferFrom(
address _from,
address _to,
uint256 _id,
uint256 _amount,
bytes calldata _data
) external;
/**
* @dev
* Safe transfer a batch of NFTs _from _to
**/
function safeBatchTransferFrom(
address _from,
address _to,
uint256[] calldata _ids,
uint256[] calldata _amounts,
bytes calldata _data
) external;
/**
* @dev
* Get max supply for token id
**/
function maxSupply(uint256 _id) external view returns (uint256);
/**
* @dev
* Get the Tier based on the NFT Id
**/
function getTierByNFTId(uint256 _nftId) external view returns (uint256);
}
/**
* @title SafeERC20
* @dev Wrappers around ERC20 operations that throw on failure (when the token
* contract returns false). Tokens that return no value (and instead revert or
* throw on failure) are also supported, non-reverting calls are assumed to be
* successful.
* To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,
* which allows you to call the safe operations as `token.safeTransfer(...)`, etc.
*/
library SafeERC20 {
using Address for address;
function safeTransfer(IERC20 token, address to, uint256 value) internal {
_callOptionalReturn(
token,
abi.encodeWithSelector(token.transfer.selector, to, value)
);
}
function safeTransferFrom(
IERC20 token,
address from,
address to,
uint256 value
) internal {
_callOptionalReturn(
token,
abi.encodeWithSelector(token.transferFrom.selector, from, to, value)
);
}
function safeIncreaseAllowance(
IERC20 token,
address spender,
uint256 value
) internal {
uint256 newAllowance = token.allowance(address(this), spender) + value;
_callOptionalReturn(
token,
abi.encodeWithSelector(
token.approve.selector,
spender,
newAllowance
)
);
}
function safeDecreaseAllowance(
IERC20 token,
address spender,
uint256 value
) internal {
unchecked {
uint256 oldAllowance = token.allowance(address(this), spender);
require(
oldAllowance >= value,
"SafeERC20: decreased allowance below zero"
);
uint256 newAllowance = oldAllowance - value;
_callOptionalReturn(
token,
abi.encodeWithSelector(
token.approve.selector,
spender,
newAllowance
)
);
}
}
/**
* @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
* on the return value: the return value is optional (but if data is returned, it must not be false).
* @param token The token targeted by the call.
* @param data The call data (encoded using abi.encode or one of its variants).
*/
function _callOptionalReturn(IERC20 token, bytes memory data) private {
// We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since
// we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that
// the target address contains contract code and also asserts for success in the low-level call.
bytes memory returndata = address(token).functionCall(
data,
"SafeERC20: low-level call failed"
);
if (returndata.length > 0) {
// Return data is optional
require(
abi.decode(returndata, (bool)),
"SafeERC20: ERC20 operation did not succeed"
);
}
}
}
/**
* @dev Staking Tier FSonic contract.
* Staking NFT:
* Every wallet can stake only one NFT at a time.
* Staking FS Tokens:
* Every wallet can stake only x tokens
*
* Staking only per wallet at a time, either for NFT or FS Tokens
**/
contract StakerTierFSonic is ERC1155Holder, AccessControl {
using SafeMath for uint256;
using SafeERC20 for IERC20;
ITierFactoryFSonic public tierFactory;
IERC20 public fsToken;
IERC20 public sFSToken;
// The period of lockup days before you can unstake NFT or FS tokens.
uint256 public lockupDays = 7;
// Cooldown days used after staking to calculate lockup period
uint256 public coolDownDays = 0;
// When unstaking FS tokens before lockup period, we keep 10% as a penalty
uint256 public withholdUnstakingPercentage = 10;
// The dev wallet address that penalty FS tokens are sent to
address private devWallet;
// Struct for the staked NFT
struct StakedTierNFT {
bool currentlyStaked;
uint256 nftId;
uint256 tierId;
uint256 creationTimestamp; // EPOCH timestamp
uint256 stakingLockupDays;
uint256 cancelStackingCoolDownDays;
}
// Tier for FS Tokens in staked contract within a certain range
struct TierFSTokens {
bool initialized;
uint256 tierId;
uint256 minFSTokens;
uint256 maxFSTokens;
}
// Struct for the staked FS tokens
struct StakedTierFSToken {
bool currentlyStaked;
uint256 tokenAmount;
uint256 tierId;
uint256 withholdUnstakingPercentage;
uint256 creationTimestamp; // EPOCH timestamp
uint256 stakingLockupDays;
uint256 cancelStackingCoolDownDays;
}
// Contains the list of Tiers based on the FS Tokens min max range
TierFSTokens[] public tierFSTokensList;
// Each wallet can only stake either NFT or FS token and also only once.
mapping(address => StakedTierNFT) public walletStakedTierNFTMapping;
mapping(address => StakedTierFSToken) public walletStakedTierFSTokenMapping;
// Events
event AddToStakedTierNFT(address staker, uint256 nftId);
event AddToStakedTierFSToken(address staker, uint256 fsTokensStaked);
event RemovedFromStakedTierNFT(address staker, uint256 nftId);
event RemovedFromStakedTierFSToken(address staker, uint256 fsTokensStaked);
event UnstakedBeforeLockupPeriodFSToken(
address staker,
uint256 fsTokensStakedReturned,
uint256 withheldFSTokens
);
// Loggers for admin only
event ChangedTierFactoryAddress(
address admin,
ITierFactoryFSonic oldTierFactoryAddress,
ITierFactoryFSonic newTierFactoryAddress
);
event ChangedLockupDays(
address admin,
uint256 oldLockupFactoryDays,
uint256 newLockupFactoryDays
);
event ChangedCoolDownDays(
address admin,
uint256 oldCoolDownDays,
uint256 newCoolDownDays
);
event ChangedDevWalletAddress(
address admin,
address oldDevWalletAddress,
address newDevWalletAddress
);
event ChangedWithholdUnstakingPercentage(
address admin,
uint256 oldUnstakingPercentage,
uint256 newUnstakingPercentage
);
event UpdateOrCreateFSTierTokenRange(
address admin,
uint256 tierId,
uint256 minFSTokens,
uint256 maxFSTokens
);
constructor(
ITierFactoryFSonic _tierFactory,
IERC20 _fsToken,
IERC20 _sFSToken,
address _devWallet
) {
_setupRole(DEFAULT_ADMIN_ROLE, msg.sender); // Add contract publisher to the admin users
tierFactory = _tierFactory;
fsToken = _fsToken;
sFSToken = _sFSToken;
devWallet = _devWallet;
}
// Needed for compiling
function supportsInterface(
bytes4 _interfaceId
)
public
view
virtual
override(ERC1155Receiver, AccessControl)
returns (bool)
{
return super.supportsInterface(_interfaceId);
}
// Getters and Setters
/**
* @dev
* Update or create a Tier FS token range
**/
function setTierFSTokenRange(
uint256 _tierId,
uint256 _minFSTokens,
uint256 _maxFSTokens
) public isAdmin {
// First check if the tier already exists and if so, update the current tier.
bool _tierExists = false;
uint256 _tierIndex = 0;
for (uint256 i = 0; i < tierFSTokensList.length; i++) {
if (tierFSTokensList[i].tierId == _tierId) {
_tierIndex = i;
_tierExists = true;
break;
}
}
if (_tierExists) {
// The tier already exists, update the existing Tier
tierFSTokensList[_tierIndex].minFSTokens = _minFSTokens;
tierFSTokensList[_tierIndex].maxFSTokens = _maxFSTokens;
} else {
// The tier does not exist, create a new entry
tierFSTokensList.push(
TierFSTokens(true, _tierId, _minFSTokens, _maxFSTokens)
);
}
emit UpdateOrCreateFSTierTokenRange(
msg.sender,
_tierId,
_minFSTokens,
_maxFSTokens
);
}
/**
* @dev
* Returns back the entire list of FS Tier tokens
**/
function getTierFSTokens()
public
view
returns (TierFSTokens[] memory tierFSTokens)
{
return tierFSTokensList;
}
/**
* @dev Replace the existing TierFactory address with a new one, only admins.
**/
function setTierFactoryAddress(
ITierFactoryFSonic _tierFactory
) public isAdmin {
ITierFactoryFSonic _oldTierFactoryAddress = tierFactory;
tierFactory = _tierFactory;
emit ChangedTierFactoryAddress(
msg.sender,
_oldTierFactoryAddress,
_tierFactory
);
}
/**
* @dev Replace the lockup_days period, only admins.
**/
function setLockupDays(uint256 _days) public isAdmin {
uint256 _oldLockupDays = lockupDays;
lockupDays = _days;
emit ChangedLockupDays(msg.sender, _oldLockupDays, _days);
}
/**
* @dev Replace the cooldowndays period, only admins.
**/
function setCoolDownDays(uint256 _days) public isAdmin {
uint256 _oldCoolDownDays = coolDownDays;
coolDownDays = _days;
emit ChangedCoolDownDays(msg.sender, _oldCoolDownDays, _days);
}
/**
* @dev Replace the dev wallet
**/
function setDevWalletAddress(address _devWallet) public isAdmin {
address _oldDevWallet = devWallet;
devWallet = _devWallet;
emit ChangedDevWalletAddress(msg.sender, _oldDevWallet, _devWallet);
}
/**
* @dev Replace the withhold unstaking percentage
**/
function setWithholdUnstakingPercentage(
uint256 _withholdUnstakingPercentage
) public isAdmin {
require(
_withholdUnstakingPercentage < 100,
"You cannot withhold more than 99 percent"
);
require(
_withholdUnstakingPercentage >= 1,
"You need to withhold at least 1 percent"
);
uint256 _oldWithholdUnstakingPercentage = withholdUnstakingPercentage;
withholdUnstakingPercentage = _withholdUnstakingPercentage;
emit ChangedWithholdUnstakingPercentage(
msg.sender,
_oldWithholdUnstakingPercentage,
_withholdUnstakingPercentage
);
}
/**
* @dev
* Returns the NFT ID currently staked
**/
function getNFTIdStaked(
address _wallet
) public view returns (uint256 nftIdStaked) {
require(
hasWalletCurrentlyStakedNFT(_wallet) == true,
"Wallet has currently no NFT staked"
);
require(
hasWalletCurrentlyStakedFSTokens(_wallet) == false,
"Wallet has staked FS Tokens and not NFTs"
);
return walletStakedTierNFTMapping[_wallet].nftId;
}
/**
* @dev
* Returns the token amount staked
**/
function getTokensAmountStaked(
address _wallet
) public view returns (uint256 tokenAmountStaked) {
require(
hasWalletCurrentlyStakedNFT(_wallet) == false,
"Wallet has staked NFTs and not FS tokens"
);
require(
hasWalletCurrentlyStakedFSTokens(_wallet) == true,
"Wallet has currently no FS Tokens staked"
);
return walletStakedTierFSTokenMapping[_wallet].tokenAmount;
}
/**
* @dev
* Returns back the Tier for staked benefits, either the token staked or NFT staked
**/
function getTierBenefitForStaker(
address _wallet
) public view returns (uint256 tierId) {
uint256 result = 0;
if (hasWalletCurrentlyStakedNFT(_wallet)) {
// If the wallet has staked NFT, get back the Tier for that NFT and return it.
result = tierFactory.getTierByNFTId(getNFTIdStaked(_wallet));
} else if (hasWalletCurrentlyStakedFSTokens(_wallet)) {
// If the wallet has staked FS tokens, calculate the TierID for the tokens staked
uint256 _fsTokenAmountToStake = walletStakedTierFSTokenMapping[
_wallet
].tokenAmount;
result = getTierIdFromTokensStaked(_fsTokenAmountToStake);
}
return result;
}
/**
* @dev
* Returns back the Tier for the Tokens staked
**/
function getTierIdFromTokensStaked(
uint256 _tokensStaked
) public view returns (uint256 tierId) {
uint256 result = 0;
for (uint256 i = 0; i < tierFSTokensList.length; i++) {
if (
_tokensStaked >= tierFSTokensList[i].minFSTokens &&
_tokensStaked <= tierFSTokensList[i].maxFSTokens
) {
result = tierFSTokensList[i].tierId;
break;
}
}
return result;
}
/**
* @dev Returns uint256 lockupTime left for staked address for NFT Staked
**/
function getLockupTimeLeftStakedNFT(
address _wallet
) public view returns (uint256 lockupTimeLeft) {
require(
hasWalletCurrentlyStakedNFT(_wallet) == true,
"Wallet has currently no NFT staked"
);
require(
hasWalletCurrentlyStakedFSTokens(_wallet) == false,
"Wallet has staked FS Tokens and not NFTs"
);
StakedTierNFT memory _stakedTierNFT = walletStakedTierNFTMapping[
_wallet
];
uint256 result = 0;
if (
(_stakedTierNFT.creationTimestamp +
(_stakedTierNFT.stakingLockupDays * 1 days) -
block.timestamp) > 0
) {
result =
_stakedTierNFT.creationTimestamp +
(_stakedTierNFT.stakingLockupDays * 1 days) -
block.timestamp;
}
return result;
}
/**
* @dev Returns uint256 lockupTime left for staked address for Tokens Stakend
**/
function getLockupTimeLeftStakedFSTokens(
address _wallet
) public view returns (uint256 lockupTimeLeft) {
require(
hasWalletCurrentlyStakedNFT(_wallet) == false,
"Wallet has staked NFTs and not FS tokens"
);
require(
hasWalletCurrentlyStakedFSTokens(_wallet) == true,
"Wallet has currently no FS Tokens staked"
);
StakedTierFSToken
memory _stakedTierFSToken = walletStakedTierFSTokenMapping[_wallet];
uint256 result = 0;
if (
(_stakedTierFSToken.creationTimestamp +
(_stakedTierFSToken.stakingLockupDays * 1 days) -
block.timestamp) > 0
) {
result =
_stakedTierFSToken.creationTimestamp +
(_stakedTierFSToken.stakingLockupDays * 1 days) -
block.timestamp;
}
return result;
}
// Checks
/**
* @dev Check if account has any Completed staked NFTs for Tier
**/
function hasWalletCompletedStakingNFT(
address _wallet
) public view returns (bool hasCompletedStakingNFT) {
bool result = true;
// 1. get the staked NFT object
StakedTierNFT memory _stakedTierNFT = walletStakedTierNFTMapping[
_wallet
];
// 2. Check if the lockup period is still counting
// If the creationTimestamp with added lockupDays is equal or bigger than now, then the auction has expired
if (
_stakedTierNFT.creationTimestamp +
_stakedTierNFT.stakingLockupDays *
1 days >=
block.timestamp
) {
result = false;
}
return result;
}
/**
* @dev Check if account has any Completed staked FS Tokens for Tier
**/
function hasWalletCompletedStakingFSTokens(
address _wallet
) public view returns (bool hasCompletedStakingFSTokens) {
bool result = true;
// 1. get the staked NFT object
StakedTierFSToken
memory _stakedTierFSToken = walletStakedTierFSTokenMapping[_wallet];
// 2. Check if the lockup period is still counting
// If the creationTimestamp with added lockupDays is equal or bigger than now, then the auction has expired
if (
_stakedTierFSToken.creationTimestamp +
_stakedTierFSToken.stakingLockupDays *
1 days >=
block.timestamp
) {
result = false;
}
return result;
}
/**
* @dev Check if address has already staked for another NFT Tier
**/
function hasWalletCurrentlyStakedNFT(
address _wallet
) public view returns (bool hasStakedNFT) {
bool result = false;
if (walletStakedTierNFTMapping[_wallet].currentlyStaked == true) {
result = true;
}
return result;
}
/**
* @dev Check if address has already staked for Tokens
**/
function hasWalletCurrentlyStakedFSTokens(
address _wallet
) public view returns (bool hasStakedFSTokens) {
bool result = false;
if (walletStakedTierFSTokenMapping[_wallet].currentlyStaked == true) {
result = true;
}
return result;
}
/**
* @dev Returns true if address can cancel staked NFT
**/
function hasCancelCoolDownDaysExpiredForStakedNFT(
address _wallet
) public view returns (bool expired) {
require(
hasWalletCurrentlyStakedNFT(_wallet) == true,
"You have currently no NFT staked"
);
require(
hasWalletCompletedStakingNFT(_wallet) == true,
"Lockup period still pending"
);
bool result = true;
// 1. get the staked NFT object
StakedTierNFT memory _stakedTierNFT = walletStakedTierNFTMapping[
_wallet
];
// 2. Check if the cool down period has expired
// If the creationTimestamp with added lockupDays is equal or bigger than now, then the auction has expired
if (
_stakedTierNFT.creationTimestamp +
(_stakedTierNFT.stakingLockupDays * 1 days) +
(_stakedTierNFT.cancelStackingCoolDownDays * 1 days) >=
block.timestamp
) {
result = false;
}
return result;
}
// BusinessLogic
/**
* @dev Transfers the NFT of the msg.sender to this contract to be staked
* You can only stake once per wallet
*/
function stakeTierNFT(uint256 _nftId) public {
require(
tierFactory.balanceOf(msg.sender, _nftId) > 0,
"You do not own this NFT"
);
require(
hasWalletCurrentlyStakedNFT(msg.sender) == false,
"You have already staked NFTs"
);
require(
hasWalletCurrentlyStakedFSTokens(msg.sender) == false,
"You have already staked FSTokens"
);
// SafeTransfer the NFT from the msg.sender to the contract
tierFactory.safeTransferFrom(msg.sender, address(this), _nftId, 1, "");
// Create a new staking NFT object and add them to the mapping
uint256 _tierId = tierFactory.getTierByNFTId(_nftId);
walletStakedTierNFTMapping[msg.sender] = StakedTierNFT(
true,
_nftId,
_tierId,
block.timestamp,
lockupDays,
coolDownDays
);
// Emit event
emit AddToStakedTierNFT(msg.sender, _nftId);
}
/**
* @dev Transfers the FSTokens of the msg.sender to this contract to be staked.
* Wallet can only stake once per wallet
**/
function stakeTierFSTokens(uint256 _fsTokenAmountToStake) public {
require(
fsToken.balanceOf(msg.sender) >= _fsTokenAmountToStake,
"You do not own enough tokens to stake"
);
require(
hasWalletCurrentlyStakedNFT(msg.sender) == false,
"You have already staked NFTs"
);
require(
hasWalletCurrentlyStakedFSTokens(msg.sender) == false,
"You have already staked FSTokens"
);
// SafeTransfer the tokens from msg.sender to this contract
fsToken.safeTransferFrom(
msg.sender,
address(this),
_fsTokenAmountToStake
);
// Mint sFS tokens
sFSToken.mintToken(msg.sender, _fsTokenAmountToStake);
// Get the Tier Id from the amount of _fsTokenAmountToStake
uint256 _tierId = getTierIdFromTokensStaked(_fsTokenAmountToStake);
// Create a new staking FSToken object and add them to the mapping
walletStakedTierFSTokenMapping[msg.sender] = StakedTierFSToken(
true,
_fsTokenAmountToStake,
_tierId,
withholdUnstakingPercentage,
block.timestamp,
lockupDays,
coolDownDays
);
// Emit event
emit AddToStakedTierFSToken(msg.sender, _fsTokenAmountToStake);
}
/**
* @dev Add more tokens to Staked FS Tokens
**/
function updateCurrentStakedFSTokens(uint256 _fsTokenAmountToStake) public {
require(
fsToken.balanceOf(msg.sender) >= _fsTokenAmountToStake,
"You do not own enough tokens to stake"
);
require(
hasWalletCurrentlyStakedNFT(msg.sender) == false,
"You have already staked NFTs"
);
require(
hasWalletCurrentlyStakedFSTokens(msg.sender) == true,
"You do not have staked FSTokens"
);
// SafeTransfer the tokens from msg.sender to this contract
fsToken.safeTransferFrom(
msg.sender,
address(this),
_fsTokenAmountToStake
);
// Mint sFS tokens
sFSToken.mintToken(msg.sender, _fsTokenAmountToStake);
// Create a new staking FSToken object and add them to the mapping
walletStakedTierFSTokenMapping[msg.sender].tokenAmount =
walletStakedTierFSTokenMapping[msg.sender].tokenAmount +
_fsTokenAmountToStake;
// Update the Tier id
uint256 _tierId = getTierIdFromTokensStaked(
walletStakedTierFSTokenMapping[msg.sender].tokenAmount
);
walletStakedTierFSTokenMapping[msg.sender].tierId = _tierId;
// Reset the lockup period in days
walletStakedTierFSTokenMapping[msg.sender].creationTimestamp = block
.timestamp;
// Emit event
emit AddToStakedTierFSToken(msg.sender, _fsTokenAmountToStake);
}
/**
* @dev Cancels the staked NFT and returns it to the owner
*/
function unstakeTierNFT() public {
require(
hasWalletCurrentlyStakedNFT(msg.sender) == true,
"You have currently no NFT staked"
);
require(
hasWalletCompletedStakingNFT(msg.sender) == true,
"Lockup period still pending"
);
require(
hasCancelCoolDownDaysExpiredForStakedNFT(msg.sender) == true,
"You need to wait for the cool down period to expire"
);
// 1. get the staked NFT object
StakedTierNFT memory _stakedTierNFT = walletStakedTierNFTMapping[
msg.sender
];
// 2. Since the staking lockup period has expired, transfer the NFT back to the owner
// SafeTransfer the NFT from the msg.sender to the contract
tierFactory.safeTransferFrom(
address(this),
msg.sender,
_stakedTierNFT.nftId,
1,
""
);
// 3. Remove the StakedTierNFT Object from the mapping
delete walletStakedTierNFTMapping[msg.sender];
// Emit event
emit RemovedFromStakedTierNFT(msg.sender, _stakedTierNFT.nftId);
}
/**
* @dev Unstake FS Tokens after lockup period
*/
function unstakeTierFSTokensAfterLockupPeriod() public {
require(
hasWalletCurrentlyStakedFSTokens(msg.sender) == true,
"You have no FSTokens staked"
);
require(
hasWalletCompletedStakingFSTokens(msg.sender) == true,
"Lockup period still pending"
);
// 1. get the staked NFT object
StakedTierFSToken
memory _stakedTierFSToken = walletStakedTierFSTokenMapping[
msg.sender
];
require(
sFSToken.balanceOf(msg.sender) >= _stakedTierFSToken.tokenAmount,
"You don't have enough sFS token!"
);
// 2. Since the staking lockup period has expired, transfer the FS Tokens back to the owner
// SafeTransfer the FSTokens from the contract to the msg.sender
fsToken.safeTransfer(msg.sender, _stakedTierFSToken.tokenAmount);
// burn sFS tokens of user
sFSToken.burnFrom(msg.sender, _stakedTierFSToken.tokenAmount);
// 3. Remove the StakedTierFSToken Object from the mapping
delete walletStakedTierFSTokenMapping[msg.sender];
// Emit event
emit RemovedFromStakedTierFSToken(
msg.sender,
_stakedTierFSToken.tokenAmount
);
}
/**
* @dev Unstake FS Token while lockup period still pending
**/
function unstakeTierFSTokensBeforeLockupPeriod() public {
require(
hasWalletCurrentlyStakedFSTokens(msg.sender) == true,
"You have no FSTokens staked"
);
require(
hasWalletCompletedStakingFSTokens(msg.sender) == false,
"Lockup period has expired"
);
// 1. get the staked NFT object
StakedTierFSToken
memory _stakedTierFSToken = walletStakedTierFSTokenMapping[
msg.sender
];
require(
sFSToken.balanceOf(msg.sender) >= _stakedTierFSToken.tokenAmount,
"You don't have enough sFS token!"
);
uint256 _fsTokensToReturnToStaker = 0;
uint256 _fsTokensPenaltyToDevWallet = 0;
// 2. Set the tokens that need to be returned
_fsTokensPenaltyToDevWallet =
(_stakedTierFSToken.tokenAmount *
_stakedTierFSToken.withholdUnstakingPercentage) /
100;
_fsTokensToReturnToStaker =
_stakedTierFSToken.tokenAmount -
_fsTokensPenaltyToDevWallet;
// 3. Safe transfer the tokens to the dev wallet and the staker
fsToken.safeTransfer(msg.sender, _fsTokensToReturnToStaker);
fsToken.safeTransfer(devWallet, _fsTokensPenaltyToDevWallet);
// burn sFS tokens of user
sFSToken.burnFrom(msg.sender, _stakedTierFSToken.tokenAmount);
// 4. Remove the StakedTierFSToken Object from the mapping
delete walletStakedTierFSTokenMapping[msg.sender];
// Emit event
emit UnstakedBeforeLockupPeriodFSToken(
msg.sender,
_fsTokensToReturnToStaker,
_fsTokensPenaltyToDevWallet
);
}
}Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"contract ITierFactoryFSonic","name":"_tierFactory","type":"address"},{"internalType":"contract IERC20","name":"_fsToken","type":"address"},{"internalType":"contract IERC20","name":"_sFSToken","type":"address"},{"internalType":"address","name":"_devWallet","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"staker","type":"address"},{"indexed":false,"internalType":"uint256","name":"fsTokensStaked","type":"uint256"}],"name":"AddToStakedTierFSToken","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"staker","type":"address"},{"indexed":false,"internalType":"uint256","name":"nftId","type":"uint256"}],"name":"AddToStakedTierNFT","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"uint256","name":"oldCoolDownDays","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"newCoolDownDays","type":"uint256"}],"name":"ChangedCoolDownDays","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"address","name":"oldDevWalletAddress","type":"address"},{"indexed":false,"internalType":"address","name":"newDevWalletAddress","type":"address"}],"name":"ChangedDevWalletAddress","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"uint256","name":"oldLockupFactoryDays","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"newLockupFactoryDays","type":"uint256"}],"name":"ChangedLockupDays","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"contract ITierFactoryFSonic","name":"oldTierFactoryAddress","type":"address"},{"indexed":false,"internalType":"contract ITierFactoryFSonic","name":"newTierFactoryAddress","type":"address"}],"name":"ChangedTierFactoryAddress","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"uint256","name":"oldUnstakingPercentage","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"newUnstakingPercentage","type":"uint256"}],"name":"ChangedWithholdUnstakingPercentage","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"staker","type":"address"},{"indexed":false,"internalType":"uint256","name":"fsTokensStaked","type":"uint256"}],"name":"RemovedFromStakedTierFSToken","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"staker","type":"address"},{"indexed":false,"internalType":"uint256","name":"nftId","type":"uint256"}],"name":"RemovedFromStakedTierNFT","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"previousAdminRole","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"newAdminRole","type":"bytes32"}],"name":"RoleAdminChanged","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleGranted","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"role","type":"bytes32"},{"indexed":true,"internalType":"address","name":"account","type":"address"},{"indexed":true,"internalType":"address","name":"sender","type":"address"}],"name":"RoleRevoked","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"staker","type":"address"},{"indexed":false,"internalType":"uint256","name":"fsTokensStakedReturned","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"withheldFSTokens","type":"uint256"}],"name":"UnstakedBeforeLockupPeriodFSToken","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"admin","type":"address"},{"indexed":false,"internalType":"uint256","name":"tierId","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"minFSTokens","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"maxFSTokens","type":"uint256"}],"name":"UpdateOrCreateFSTierTokenRange","type":"event"},{"inputs":[],"name":"DEFAULT_ADMIN_ROLE","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"coolDownDays","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"fsToken","outputs":[{"internalType":"contract IERC20","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"getLockupTimeLeftStakedFSTokens","outputs":[{"internalType":"uint256","name":"lockupTimeLeft","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"getLockupTimeLeftStakedNFT","outputs":[{"internalType":"uint256","name":"lockupTimeLeft","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"getNFTIdStaked","outputs":[{"internalType":"uint256","name":"nftIdStaked","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"}],"name":"getRoleAdmin","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"getTierBenefitForStaker","outputs":[{"internalType":"uint256","name":"tierId","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getTierFSTokens","outputs":[{"components":[{"internalType":"bool","name":"initialized","type":"bool"},{"internalType":"uint256","name":"tierId","type":"uint256"},{"internalType":"uint256","name":"minFSTokens","type":"uint256"},{"internalType":"uint256","name":"maxFSTokens","type":"uint256"}],"internalType":"struct StakerTierFSonic.TierFSTokens[]","name":"tierFSTokens","type":"tuple[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tokensStaked","type":"uint256"}],"name":"getTierIdFromTokensStaked","outputs":[{"internalType":"uint256","name":"tierId","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"getTokensAmountStaked","outputs":[{"internalType":"uint256","name":"tokenAmountStaked","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"grantRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"hasCancelCoolDownDaysExpiredForStakedNFT","outputs":[{"internalType":"bool","name":"expired","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"hasRole","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"hasWalletCompletedStakingFSTokens","outputs":[{"internalType":"bool","name":"hasCompletedStakingFSTokens","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"hasWalletCompletedStakingNFT","outputs":[{"internalType":"bool","name":"hasCompletedStakingNFT","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"hasWalletCurrentlyStakedFSTokens","outputs":[{"internalType":"bool","name":"hasStakedFSTokens","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_wallet","type":"address"}],"name":"hasWalletCurrentlyStakedNFT","outputs":[{"internalType":"bool","name":"hasStakedNFT","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"lockupDays","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256[]","name":"","type":"uint256[]"},{"internalType":"uint256[]","name":"","type":"uint256[]"},{"internalType":"bytes","name":"","type":"bytes"}],"name":"onERC1155BatchReceived","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"uint256","name":"","type":"uint256"},{"internalType":"bytes","name":"","type":"bytes"}],"name":"onERC1155Received","outputs":[{"internalType":"bytes4","name":"","type":"bytes4"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"renounceRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"role","type":"bytes32"},{"internalType":"address","name":"account","type":"address"}],"name":"revokeRole","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"sFSToken","outputs":[{"internalType":"contract IERC20","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_days","type":"uint256"}],"name":"setCoolDownDays","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_devWallet","type":"address"}],"name":"setDevWalletAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_days","type":"uint256"}],"name":"setLockupDays","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_tierId","type":"uint256"},{"internalType":"uint256","name":"_minFSTokens","type":"uint256"},{"internalType":"uint256","name":"_maxFSTokens","type":"uint256"}],"name":"setTierFSTokenRange","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"contract ITierFactoryFSonic","name":"_tierFactory","type":"address"}],"name":"setTierFactoryAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_withholdUnstakingPercentage","type":"uint256"}],"name":"setWithholdUnstakingPercentage","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_fsTokenAmountToStake","type":"uint256"}],"name":"stakeTierFSTokens","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_nftId","type":"uint256"}],"name":"stakeTierNFT","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes4","name":"_interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"tierFSTokensList","outputs":[{"internalType":"bool","name":"initialized","type":"bool"},{"internalType":"uint256","name":"tierId","type":"uint256"},{"internalType":"uint256","name":"minFSTokens","type":"uint256"},{"internalType":"uint256","name":"maxFSTokens","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"tierFactory","outputs":[{"internalType":"contract ITierFactoryFSonic","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"unstakeTierFSTokensAfterLockupPeriod","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"unstakeTierFSTokensBeforeLockupPeriod","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"unstakeTierNFT","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_fsTokenAmountToStake","type":"uint256"}],"name":"updateCurrentStakedFSTokens","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"walletStakedTierFSTokenMapping","outputs":[{"internalType":"bool","name":"currentlyStaked","type":"bool"},{"internalType":"uint256","name":"tokenAmount","type":"uint256"},{"internalType":"uint256","name":"tierId","type":"uint256"},{"internalType":"uint256","name":"withholdUnstakingPercentage","type":"uint256"},{"internalType":"uint256","name":"creationTimestamp","type":"uint256"},{"internalType":"uint256","name":"stakingLockupDays","type":"uint256"},{"internalType":"uint256","name":"cancelStackingCoolDownDays","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"walletStakedTierNFTMapping","outputs":[{"internalType":"bool","name":"currentlyStaked","type":"bool"},{"internalType":"uint256","name":"nftId","type":"uint256"},{"internalType":"uint256","name":"tierId","type":"uint256"},{"internalType":"uint256","name":"creationTimestamp","type":"uint256"},{"internalType":"uint256","name":"stakingLockupDays","type":"uint256"},{"internalType":"uint256","name":"cancelStackingCoolDownDays","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"withholdUnstakingPercentage","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"}]Contract Creation Code
608060405260076004556000600555600a6006553480156200002057600080fd5b50604051620033783803806200337883398101604081905262000043916200016d565b62000050600033620000a4565b600180546001600160a01b039586166001600160a01b0319918216179091556002805494861694821694909417909355600380549285169284169290921790915560078054919093169116179055620001d5565b620000b08282620000b4565b5050565b6000828152602081815260408083206001600160a01b038516845290915290205460ff16620000b0576000828152602081815260408083206001600160a01b03851684529091529020805460ff19166001179055620001103390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b6001600160a01b03811681146200016a57600080fd5b50565b600080600080608085870312156200018457600080fd5b8451620001918162000154565b6020860151909450620001a48162000154565b6040860151909350620001b78162000154565b6060860151909250620001ca8162000154565b939692955090935050565b61319380620001e56000396000f3fe608060405234801561001057600080fd5b506004361061025e5760003560e01c8063842b047e11610146578063bc197c81116100c3578063d87b59cc11610087578063d87b59cc14610631578063d92456cb14610644578063ddadd90f14610657578063e1a4f14a1461066a578063e406bbbd1461067d578063f23a6e611461069057600080fd5b8063bc197c8114610545578063c213fa591461057d578063d0dd52aa14610585578063d547741f1461060b578063d859345f1461061e57600080fd5b806398bc695d1161010a57806398bc695d146104fb578063a217fddf14610504578063a2b70e591461050c578063b55c4eb51461051f578063b96437b41461053257600080fd5b8063842b047e146104a557806390273901146104b857806391d14854146104c057806393c310b7146104d35780639627ffe9146104e657600080fd5b806336568abe116101df578063554a7060116101a3578063554a706014610403578063583d5a8314610416578063587e77361461041f5780635a2f80a01461043257806373ef9e0f1461044557806374f10eb11461047057600080fd5b806336568abe1461034c5780634409eea11461035f57806346d77162146103675780635040df9a1461037a578063523280861461038d57600080fd5b8063201d607611610226578063201d6076146102dd578063248a9ca3146102f05780632d52f68c146103135780632f2ff15d1461032657806335f63aff1461033957600080fd5b806301de23511461026357806301ffc9a71461027f57806311983e53146102a257806311aec429146102b5578063120a0612146102ca575b600080fd5b61026c60055481565b6040519081526020015b60405180910390f35b61029261028d36600461298e565b6106af565b6040519015158152602001610276565b61026c6102b03660046129d0565b6106c0565b6102c86102c33660046129ed565b6107ea565b005b6102c86102d83660046129d0565b610859565b6102c86102eb366004612a06565b6108e1565b61026c6102fe3660046129ed565b60009081526020819052604090206001015490565b61026c6103213660046129d0565b610aea565b6102c8610334366004612a32565b610c01565b6102c86103473660046129ed565b610c2c565b6102c861035a366004612a32565b610e7d565b6102c8610efb565b6102c86103753660046129ed565b611219565b6102926103883660046129d0565b6114dc565b6103d461039b3660046129d0565b60096020526000908152604090208054600182015460028301546003840154600485015460059095015460ff9094169492939192909186565b6040805196151587526020870195909552938501929092526060840152608083015260a082015260c001610276565b6102c86104113660046129ed565b611571565b61026c60065481565b61029261042d3660046129d0565b611696565b6102c86104403660046129ed565b6117be565b600254610458906001600160a01b031681565b6040516001600160a01b039091168152602001610276565b61048361047e3660046129ed565b611821565b6040805194151585526020850193909352918301526060820152608001610276565b600154610458906001600160a01b031681565b6102c861185f565b6102926104ce366004612a32565b611a8e565b61026c6104e13660046129d0565b611ab7565b6104ee611b28565b6040516102769190612a62565b61026c60045481565b61026c600081565b6102c861051a3660046129d0565b611bae565b61029261052d3660046129d0565b611c36565b600354610458906001600160a01b031681565b610564610553366004612bf4565b63bc197c8160e01b95945050505050565b6040516001600160e01b03199091168152602001610276565b6102c8611c66565b6105d46105933660046129d0565b600a60205260009081526040902080546001820154600283015460038401546004850154600586015460069096015460ff9095169593949293919290919087565b6040805197151588526020880196909652948601939093526060850191909152608084015260a083015260c082015260e001610276565b6102c8610619366004612a32565b611eff565b61026c61062c3660046129d0565b611f25565b6102c861063f3660046129ed565b611f96565b6102926106523660046129d0565b6121aa565b6102926106653660046129d0565b612238565b61026c6106783660046129ed565b612268565b61026c61068b3660046129d0565b612312565b61056461069e366004612ca2565b63f23a6e6160e01b95945050505050565b60006106ba826123de565b92915050565b60006106cb82612238565b15156001146106f55760405162461bcd60e51b81526004016106ec90612d0b565b60405180910390fd5b6106fe82611c36565b1561071b5760405162461bcd60e51b81526004016106ec90612d4d565b6001600160a01b0382166000908152600960209081526040808320815160c081018352815460ff16151581526001820154938101939093526002810154918301919091526003810154606083015260048101546080830181905260059091015460a0830152909190819042906107949062015180612dab565b84606001516107a39190612dc2565b6107ad9190612dd5565b11156107e357428260800151620151806107c79190612dab565b83606001516107d69190612dc2565b6107e09190612dd5565b90505b9392505050565b6107f5600033611a8e565b6108115760405162461bcd60e51b81526004016106ec90612de8565b60048054908290556040517f339b9229beac0da59bc8ab4913b1e81b018cae9ecef830c573c53deeb87f5c529061084d90339084908690612e1d565b60405180910390a15050565b610864600033611a8e565b6108805760405162461bcd60e51b81526004016106ec90612de8565b600780546001600160a01b031981166001600160a01b0384811691821790935560408051338152939092166020840181905291830152907f51b66e0e5bd72224dd75c35b693ad62bd75766bdb04230e2c8c218752c51408a9060600161084d565b6108ec600033611a8e565b6109085760405162461bcd60e51b81526004016106ec90612de8565b60008060005b60085481101561096157856008828154811061092c5761092c612e3e565b9060005260206000209060040201600101540361094f5780915060019250610961565b8061095981612e54565b91505061090e565b5081156109bf57836008828154811061097c5761097c612e3e565b90600052602060002090600402016002018190555082600882815481106109a5576109a5612e3e565b906000526020600020906004020160030181905550610a9b565b604080516080810182526001808252602082018881529282018781526060830187815260088054938401815560005292517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee36004909302928301805460ff191691151591909117905592517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee482015591517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee5830155517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee6909101555b6040805133815260208101879052908101859052606081018490527ffd30965e9c468e5413ad2a3fa0324386fcf45de8135726765a66c121bf9b09e39060800160405180910390a15050505050565b6000610af582612238565b15610b125760405162461bcd60e51b81526004016106ec90612e6d565b610b1b82611c36565b1515600114610b3c5760405162461bcd60e51b81526004016106ec90612eb5565b6001600160a01b0382166000908152600a60209081526040808320815160e081018352815460ff16151581526001820154938101939093526002810154918301919091526003810154606083015260048101546080830152600581015460a0830181905260069091015460c083015290919081904290610bbf9062015180612dab565b8460800151610bce9190612dc2565b610bd89190612dd5565b11156107e357428260a0015162015180610bf29190612dab565b83608001516107d69190612dc2565b600082815260208190526040902060010154610c1d8133612403565b610c278383612467565b505050565b6002546040516370a0823160e01b815233600482015282916001600160a01b0316906370a0823190602401602060405180830381865afa158015610c74573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c989190612efd565b1015610cb65760405162461bcd60e51b81526004016106ec90612f16565b610cbf33612238565b15610cdc5760405162461bcd60e51b81526004016106ec90612f5b565b610ce533611c36565b15610d325760405162461bcd60e51b815260206004820181905260248201527f596f75206861766520616c7265616479207374616b6564204653546f6b656e7360448201526064016106ec565b600254610d4a906001600160a01b03163330846124eb565b600354604051630f38ca0d60e31b81526001600160a01b03909116906379c6506890610d7c9033908590600401612f92565b600060405180830381600087803b158015610d9657600080fd5b505af1158015610daa573d6000803e3d6000fd5b505050506000610db982612268565b6040805160e08101825260018082526020808301878152838501868152600680546060870190815242608088019081526004805460a08a019081526005805460c08c01908152336000818152600a909b52998d90209b518c5460ff1916901515178c559751998b0199909955945160028a015591516003890155519087015590519385019390935551929091019190915590519192507f7d9127a72910ce617963edba28318ea738f771668f124319bd636c523b24ac0b9161084d91908590612f92565b6001600160a01b0381163314610eed5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b60648201526084016106ec565b610ef7828261255c565b5050565b610f0433611c36565b1515600114610f555760405162461bcd60e51b815260206004820152601b60248201527f596f752068617665206e6f204653546f6b656e73207374616b6564000000000060448201526064016106ec565b610f5e336121aa565b15610fab5760405162461bcd60e51b815260206004820152601960248201527f4c6f636b757020706572696f642068617320657870697265640000000000000060448201526064016106ec565b336000818152600a6020908152604091829020825160e081018452815460ff1615158152600182015492810183905260028201548185015260038083015460608301526004808401546080840152600584015460a084015260069093015460c08301525493516370a0823160e01b81529182019490945290916001600160a01b0316906370a0823190602401602060405180830381865afa158015611054573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110789190612efd565b10156110c65760405162461bcd60e51b815260206004820181905260248201527f596f7520646f6e2774206861766520656e6f7567682073465320746f6b656e2160448201526064016106ec565b6000806064836060015184602001516110df9190612dab565b6110e99190612fab565b90508083602001516110fb9190612dd5565b600254909250611115906001600160a01b031633846125c1565b600754600254611132916001600160a01b039182169116836125c1565b600354602084015160405163079cc67960e41b81526001600160a01b03909216916379cc67909161116891339190600401612f92565b600060405180830381600087803b15801561118257600080fd5b505af1158015611196573d6000803e3d6000fd5b5050336000818152600a6020526040808220805460ff19168155600181018390556002810183905560038101839055600481018390556005810183905560060191909155517fa20e94ac360e12a963d3b1a4111d5d6cebcab4db627c9a6479c6dad34610c7f1935061120c925085908590612e1d565b60405180910390a1505050565b600154604051627eeac760e11b81526000916001600160a01b03169062fdd58e9061124a9033908690600401612f92565b602060405180830381865afa158015611267573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128b9190612efd565b116112d85760405162461bcd60e51b815260206004820152601760248201527f596f7520646f206e6f74206f776e2074686973204e465400000000000000000060448201526064016106ec565b6112e133612238565b156112fe5760405162461bcd60e51b81526004016106ec90612f5b565b61130733611c36565b156113545760405162461bcd60e51b815260206004820181905260248201527f596f75206861766520616c7265616479207374616b6564204653546f6b656e7360448201526064016106ec565b60018054604051637921219560e11b81526001600160a01b039091169163f242432a9161138991339130918791600401612fcd565b600060405180830381600087803b1580156113a357600080fd5b505af11580156113b7573d6000803e3d6000fd5b5050600154604051634551169d60e01b815260048101859052600093506001600160a01b039091169150634551169d90602401602060405180830381865afa158015611407573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061142b9190612efd565b6040805160c08101825260018082526020808301878152838501868152426060860190815260048054608088019081526005805460a08a019081523360008181526009909952978b902099518a5460ff1916901515178a55955197890197909755925160028801559051600387015590519085015551929091019190915590519192507fae60b3ca24281aea6e75782e0e5a980a7dd9ee173e63fb212a8c0def1fc6efe79161084d91908590612f92565b6001600160a01b0381166000908152600960209081526040808320815160c081018352815460ff1615158152600182810154948201949094526002820154928101929092526003810154606083015260048101546080830181905260059091015460a083015242906115519062015180612dab565b82606001516115609190612dc2565b1061156a57600091505b5092915050565b61157c600033611a8e565b6115985760405162461bcd60e51b81526004016106ec90612de8565b606481106115f95760405162461bcd60e51b815260206004820152602860248201527f596f752063616e6e6f742077697468686f6c64206d6f7265207468616e203939604482015267081c195c98d95b9d60c21b60648201526084016106ec565b600181101561165a5760405162461bcd60e51b815260206004820152602760248201527f596f75206e65656420746f2077697468686f6c64206174206c656173742031206044820152661c195c98d95b9d60ca1b60648201526084016106ec565b60068054908290556040517fbed291e013058f2243e71b2170f425b3c4819b155f012b92e4492b3ad3e866849061084d90339084908690612e1d565b60006116a182612238565b15156001146116f25760405162461bcd60e51b815260206004820181905260248201527f596f7520686176652063757272656e746c79206e6f204e4654207374616b656460448201526064016106ec565b6116fb826114dc565b151560011461171c5760405162461bcd60e51b81526004016106ec90613005565b6001600160a01b038216600090815260096020908152604091829020825160c081018452815460ff16151581526001828101549382019390935260028201549381019390935260038101546060840152600481015460808401526005015460a0830181905290919042906117939062015180612dab565b60808301516117a59062015180612dab565b83606001516117b49190612dc2565b6115609190612dc2565b6117c9600033611a8e565b6117e55760405162461bcd60e51b81526004016106ec90612de8565b60058054908290556040517fdb8d38150b9bb879c12291844bcd9c914b7c4666ae198f4db69a5a5176d13ee89061084d90339084908690612e1d565b6008818154811061183157600080fd5b6000918252602090912060049091020180546001820154600283015460039093015460ff9092169350919084565b61186833612238565b15156001146118b95760405162461bcd60e51b815260206004820181905260248201527f596f7520686176652063757272656e746c79206e6f204e4654207374616b656460448201526064016106ec565b6118c2336114dc565b15156001146118e35760405162461bcd60e51b81526004016106ec90613005565b6118ec33611696565b15156001146119595760405162461bcd60e51b815260206004820152603360248201527f596f75206e65656420746f207761697420666f722074686520636f6f6c20646f604482015272776e20706572696f6420746f2065787069726560681b60648201526084016106ec565b33600081815260096020908152604091829020825160c081018452815460ff161515815260018083015493820184905260028301548286015260038301546060830152600480840154608084015260059093015460a083015280549451637921219560e11b815291956001600160a01b039095169463f242432a946119e49430949293919201612fcd565b600060405180830381600087803b1580156119fe57600080fd5b505af1158015611a12573d6000803e3d6000fd5b5050336000818152600960209081526040808320805460ff19168155600181018490556002810184905560038101849055600481018490556005019290925585015190517fb04b58934e9f7d959ec5e18634b0bc7164b689fa752fd45d2f20f8ccfa33cab19450611a839350612f92565b60405180910390a150565b6000918252602082815260408084206001600160a01b0393909316845291905290205460ff1690565b6000611ac282612238565b15611adf5760405162461bcd60e51b81526004016106ec90612e6d565b611ae882611c36565b1515600114611b095760405162461bcd60e51b81526004016106ec90612eb5565b506001600160a01b03166000908152600a602052604090206001015490565b60606008805480602002602001604051908101604052809291908181526020016000905b82821015611ba55760008481526020908190206040805160808101825260048602909201805460ff1615158352600180820154848601526002820154928401929092526003015460608301529083529092019101611b4c565b50505050905090565b611bb9600033611a8e565b611bd55760405162461bcd60e51b81526004016106ec90612de8565b600180546001600160a01b031981166001600160a01b0384811691821790935560408051338152939092166020840181905291830152907f9d5e5e35ff4b9029875bfd320e82316168739f50ec7d9b2847a08542967036789060600161084d565b6001600160a01b0381166000908152600a6020526040812054819060ff1615156001036106ba5750600192915050565b611c6f33611c36565b1515600114611cc05760405162461bcd60e51b815260206004820152601b60248201527f596f752068617665206e6f204653546f6b656e73207374616b6564000000000060448201526064016106ec565b611cc9336121aa565b1515600114611cea5760405162461bcd60e51b81526004016106ec90613005565b336000818152600a6020908152604091829020825160e081018452815460ff1615158152600182015492810183905260028201548185015260038083015460608301526004808401546080840152600584015460a084015260069093015460c08301525493516370a0823160e01b81529182019490945290916001600160a01b0316906370a0823190602401602060405180830381865afa158015611d93573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611db79190612efd565b1015611e055760405162461bcd60e51b815260206004820181905260248201527f596f7520646f6e2774206861766520656e6f7567682073465320746f6b656e2160448201526064016106ec565b6020810151600254611e24916001600160a01b039091169033906125c1565b600354602082015160405163079cc67960e41b81526001600160a01b03909216916379cc679091611e5a91339190600401612f92565b600060405180830381600087803b158015611e7457600080fd5b505af1158015611e88573d6000803e3d6000fd5b5050336000818152600a60209081526040808320805460ff1916815560018101849055600281018490556003810184905560048101849055600581018490556006019290925585015190517e0394400365c07f75e43823dbaaeed7ca6913196a36451c4a64bf7a09e6de8e9450611a839350612f92565b600082815260208190526040902060010154611f1b8133612403565b610c27838361255c565b6000611f3082612238565b1515600114611f515760405162461bcd60e51b81526004016106ec90612d0b565b611f5a82611c36565b15611f775760405162461bcd60e51b81526004016106ec90612d4d565b506001600160a01b031660009081526009602052604090206001015490565b6002546040516370a0823160e01b815233600482015282916001600160a01b0316906370a0823190602401602060405180830381865afa158015611fde573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906120029190612efd565b10156120205760405162461bcd60e51b81526004016106ec90612f16565b61202933612238565b156120465760405162461bcd60e51b81526004016106ec90612f5b565b61204f33611c36565b15156001146120a05760405162461bcd60e51b815260206004820152601f60248201527f596f7520646f206e6f742068617665207374616b6564204653546f6b656e730060448201526064016106ec565b6002546120b8906001600160a01b03163330846124eb565b600354604051630f38ca0d60e31b81526001600160a01b03909116906379c65068906120ea9033908590600401612f92565b600060405180830381600087803b15801561210457600080fd5b505af1158015612118573d6000803e3d6000fd5b5050336000908152600a602052604090206001015461213a9250839150612dc2565b336000908152600a602052604081206001018290559061215990612268565b336000818152600a6020526040908190206002810184905542600490910155519192507f7d9127a72910ce617963edba28318ea738f771668f124319bd636c523b24ac0b9161084d91908590612f92565b6001600160a01b0381166000908152600a60209081526040808320815160e081018352815460ff1615158152600182810154948201949094526002820154928101929092526003810154606083015260048101546080830152600581015460a0830181905260069091015460c083015242906122299062015180612dab565b82608001516115609190612dc2565b6001600160a01b038116600090815260096020526040812054819060ff1615156001036106ba5750600192915050565b600080805b60085481101561156a576008818154811061228a5761228a612e3e565b90600052602060002090600402016002015484101580156122cf5750600881815481106122b9576122b9612e3e565b9060005260206000209060040201600301548411155b1561230057600881815481106122e7576122e7612e3e565b906000526020600020906004020160010154915061156a565b8061230a81612e54565b91505061226d565b60008061231e83612238565b156123a3576001546001600160a01b0316634551169d61233d85611f25565b6040518263ffffffff1660e01b815260040161235b91815260200190565b602060405180830381865afa158015612378573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061239c9190612efd565b90506106ba565b6123ac83611c36565b156106ba576001600160a01b0383166000908152600a60205260409020600101546123d681612268565b949350505050565b60006001600160e01b03198216637965db0b60e01b14806106ba57506106ba826125e0565b61240d8282611a8e565b610ef757612425816001600160a01b03166014612615565b612430836020612615565b604051602001612441929190613060565b60408051601f198184030181529082905262461bcd60e51b82526106ec916004016130d5565b6124718282611a8e565b610ef7576000828152602081815260408083206001600160a01b03851684529091529020805460ff191660011790556124a73390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b6040516001600160a01b03808516602483015283166044820152606481018290526125569085906323b872dd60e01b906084015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b0319909316929092179091526127b1565b50505050565b6125668282611a8e565b15610ef7576000828152602081815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b610c278363a9059cbb60e01b848460405160240161251f929190612f92565b60006001600160e01b03198216630271189760e51b14806106ba57506301ffc9a760e01b6001600160e01b03198316146106ba565b60606000612624836002612dab565b61262f906002612dc2565b67ffffffffffffffff81111561264757612647612ac8565b6040519080825280601f01601f191660200182016040528015612671576020820181803683370190505b509050600360fc1b8160008151811061268c5761268c612e3e565b60200101906001600160f81b031916908160001a905350600f60fb1b816001815181106126bb576126bb612e3e565b60200101906001600160f81b031916908160001a90535060006126df846002612dab565b6126ea906001612dc2565b90505b6001811115612762576f181899199a1a9b1b9c1cb0b131b232b360811b85600f166010811061271e5761271e612e3e565b1a60f81b82828151811061273457612734612e3e565b60200101906001600160f81b031916908160001a90535060049490941c9361275b81613108565b90506126ed565b5083156107e35760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e7460448201526064016106ec565b6000612806826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166128839092919063ffffffff16565b805190915015610c275780806020019051810190612824919061311f565b610c275760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b60648201526084016106ec565b60606107e0848460008585843b6128dc5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e747261637400000060448201526064016106ec565b600080866001600160a01b031685876040516128f89190613141565b60006040518083038185875af1925050503d8060008114612935576040519150601f19603f3d011682016040523d82523d6000602084013e61293a565b606091505b509150915061294a828286612955565b979650505050505050565b606083156129645750816107e3565b8251156129745782518084602001fd5b8160405162461bcd60e51b81526004016106ec91906130d5565b6000602082840312156129a057600080fd5b81356001600160e01b0319811681146107e357600080fd5b6001600160a01b03811681146129cd57600080fd5b50565b6000602082840312156129e257600080fd5b81356107e3816129b8565b6000602082840312156129ff57600080fd5b5035919050565b600080600060608486031215612a1b57600080fd5b505081359360208301359350604090920135919050565b60008060408385031215612a4557600080fd5b823591506020830135612a57816129b8565b809150509250929050565b602080825282518282018190526000919060409081850190868401855b82811015612abb578151805115158552868101518786015285810151868601526060908101519085015260809093019290850190600101612a7f565b5091979650505050505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715612b0757612b07612ac8565b604052919050565b600082601f830112612b2057600080fd5b8135602067ffffffffffffffff821115612b3c57612b3c612ac8565b8160051b612b4b828201612ade565b9283528481018201928281019087851115612b6557600080fd5b83870192505b8483101561294a57823582529183019190830190612b6b565b600082601f830112612b9557600080fd5b813567ffffffffffffffff811115612baf57612baf612ac8565b612bc2601f8201601f1916602001612ade565b818152846020838601011115612bd757600080fd5b816020850160208301376000918101602001919091529392505050565b600080600080600060a08688031215612c0c57600080fd5b8535612c17816129b8565b94506020860135612c27816129b8565b9350604086013567ffffffffffffffff80821115612c4457600080fd5b612c5089838a01612b0f565b94506060880135915080821115612c6657600080fd5b612c7289838a01612b0f565b93506080880135915080821115612c8857600080fd5b50612c9588828901612b84565b9150509295509295909350565b600080600080600060a08688031215612cba57600080fd5b8535612cc5816129b8565b94506020860135612cd5816129b8565b93506040860135925060608601359150608086013567ffffffffffffffff811115612cff57600080fd5b612c9588828901612b84565b60208082526022908201527f57616c6c6574206861732063757272656e746c79206e6f204e4654207374616b604082015261195960f21b606082015260800190565b60208082526028908201527f57616c6c657420686173207374616b656420465320546f6b656e7320616e64206040820152676e6f74204e46547360c01b606082015260800190565b634e487b7160e01b600052601160045260246000fd5b80820281158282048414176106ba576106ba612d95565b808201808211156106ba576106ba612d95565b818103818111156106ba576106ba612d95565b6020808252818101527f4163636f756e74206973206e6f7420696e207468652061646d696e206c697374604082015260600190565b6001600160a01b039390931683526020830191909152604082015260600190565b634e487b7160e01b600052603260045260246000fd5b600060018201612e6657612e66612d95565b5060010190565b60208082526028908201527f57616c6c657420686173207374616b6564204e46547320616e64206e6f7420466040820152675320746f6b656e7360c01b606082015260800190565b60208082526028908201527f57616c6c6574206861732063757272656e746c79206e6f20465320546f6b656e6040820152671cc81cdd185ad95960c21b606082015260800190565b600060208284031215612f0f57600080fd5b5051919050565b60208082526025908201527f596f7520646f206e6f74206f776e20656e6f75676820746f6b656e7320746f206040820152647374616b6560d81b606082015260800190565b6020808252601c908201527f596f75206861766520616c7265616479207374616b6564204e46547300000000604082015260600190565b6001600160a01b03929092168252602082015260400190565b600082612fc857634e487b7160e01b600052601260045260246000fd5b500490565b6001600160a01b0394851681529290931660208301526040820152606081019190915260a06080820181905260009082015260c00190565b6020808252601b908201527f4c6f636b757020706572696f64207374696c6c2070656e64696e670000000000604082015260600190565b60005b8381101561305757818101518382015260200161303f565b50506000910152565b7f416363657373436f6e74726f6c3a206163636f756e742000000000000000000081526000835161309881601785016020880161303c565b7001034b99036b4b9b9b4b733903937b6329607d1b60179184019182015283516130c981602884016020880161303c565b01602801949350505050565b60208152600082518060208401526130f481604085016020870161303c565b601f01601f19169190910160400192915050565b60008161311757613117612d95565b506000190190565b60006020828403121561313157600080fd5b815180151581146107e357600080fd5b6000825161315381846020870161303c565b919091019291505056fea264697066735822122067d4062d6fc8607b22438ab1050c07400873052d52dc01ccb20934a8a5b1e69564736f6c634300081200330000000000000000000000004db1e329713f3b4d606f3d3956eed3eca7dc6e99000000000000000000000000bc0d0650412ef353d672c0bbd12efff90591b251000000000000000000000000a81b289dc053c242b43aed38f2b77e30dd459ec10000000000000000000000006e2a0a942eaa01b7eb2639b8b65d1d2768a87bac
Deployed Bytecode
0x608060405234801561001057600080fd5b506004361061025e5760003560e01c8063842b047e11610146578063bc197c81116100c3578063d87b59cc11610087578063d87b59cc14610631578063d92456cb14610644578063ddadd90f14610657578063e1a4f14a1461066a578063e406bbbd1461067d578063f23a6e611461069057600080fd5b8063bc197c8114610545578063c213fa591461057d578063d0dd52aa14610585578063d547741f1461060b578063d859345f1461061e57600080fd5b806398bc695d1161010a57806398bc695d146104fb578063a217fddf14610504578063a2b70e591461050c578063b55c4eb51461051f578063b96437b41461053257600080fd5b8063842b047e146104a557806390273901146104b857806391d14854146104c057806393c310b7146104d35780639627ffe9146104e657600080fd5b806336568abe116101df578063554a7060116101a3578063554a706014610403578063583d5a8314610416578063587e77361461041f5780635a2f80a01461043257806373ef9e0f1461044557806374f10eb11461047057600080fd5b806336568abe1461034c5780634409eea11461035f57806346d77162146103675780635040df9a1461037a578063523280861461038d57600080fd5b8063201d607611610226578063201d6076146102dd578063248a9ca3146102f05780632d52f68c146103135780632f2ff15d1461032657806335f63aff1461033957600080fd5b806301de23511461026357806301ffc9a71461027f57806311983e53146102a257806311aec429146102b5578063120a0612146102ca575b600080fd5b61026c60055481565b6040519081526020015b60405180910390f35b61029261028d36600461298e565b6106af565b6040519015158152602001610276565b61026c6102b03660046129d0565b6106c0565b6102c86102c33660046129ed565b6107ea565b005b6102c86102d83660046129d0565b610859565b6102c86102eb366004612a06565b6108e1565b61026c6102fe3660046129ed565b60009081526020819052604090206001015490565b61026c6103213660046129d0565b610aea565b6102c8610334366004612a32565b610c01565b6102c86103473660046129ed565b610c2c565b6102c861035a366004612a32565b610e7d565b6102c8610efb565b6102c86103753660046129ed565b611219565b6102926103883660046129d0565b6114dc565b6103d461039b3660046129d0565b60096020526000908152604090208054600182015460028301546003840154600485015460059095015460ff9094169492939192909186565b6040805196151587526020870195909552938501929092526060840152608083015260a082015260c001610276565b6102c86104113660046129ed565b611571565b61026c60065481565b61029261042d3660046129d0565b611696565b6102c86104403660046129ed565b6117be565b600254610458906001600160a01b031681565b6040516001600160a01b039091168152602001610276565b61048361047e3660046129ed565b611821565b6040805194151585526020850193909352918301526060820152608001610276565b600154610458906001600160a01b031681565b6102c861185f565b6102926104ce366004612a32565b611a8e565b61026c6104e13660046129d0565b611ab7565b6104ee611b28565b6040516102769190612a62565b61026c60045481565b61026c600081565b6102c861051a3660046129d0565b611bae565b61029261052d3660046129d0565b611c36565b600354610458906001600160a01b031681565b610564610553366004612bf4565b63bc197c8160e01b95945050505050565b6040516001600160e01b03199091168152602001610276565b6102c8611c66565b6105d46105933660046129d0565b600a60205260009081526040902080546001820154600283015460038401546004850154600586015460069096015460ff9095169593949293919290919087565b6040805197151588526020880196909652948601939093526060850191909152608084015260a083015260c082015260e001610276565b6102c8610619366004612a32565b611eff565b61026c61062c3660046129d0565b611f25565b6102c861063f3660046129ed565b611f96565b6102926106523660046129d0565b6121aa565b6102926106653660046129d0565b612238565b61026c6106783660046129ed565b612268565b61026c61068b3660046129d0565b612312565b61056461069e366004612ca2565b63f23a6e6160e01b95945050505050565b60006106ba826123de565b92915050565b60006106cb82612238565b15156001146106f55760405162461bcd60e51b81526004016106ec90612d0b565b60405180910390fd5b6106fe82611c36565b1561071b5760405162461bcd60e51b81526004016106ec90612d4d565b6001600160a01b0382166000908152600960209081526040808320815160c081018352815460ff16151581526001820154938101939093526002810154918301919091526003810154606083015260048101546080830181905260059091015460a0830152909190819042906107949062015180612dab565b84606001516107a39190612dc2565b6107ad9190612dd5565b11156107e357428260800151620151806107c79190612dab565b83606001516107d69190612dc2565b6107e09190612dd5565b90505b9392505050565b6107f5600033611a8e565b6108115760405162461bcd60e51b81526004016106ec90612de8565b60048054908290556040517f339b9229beac0da59bc8ab4913b1e81b018cae9ecef830c573c53deeb87f5c529061084d90339084908690612e1d565b60405180910390a15050565b610864600033611a8e565b6108805760405162461bcd60e51b81526004016106ec90612de8565b600780546001600160a01b031981166001600160a01b0384811691821790935560408051338152939092166020840181905291830152907f51b66e0e5bd72224dd75c35b693ad62bd75766bdb04230e2c8c218752c51408a9060600161084d565b6108ec600033611a8e565b6109085760405162461bcd60e51b81526004016106ec90612de8565b60008060005b60085481101561096157856008828154811061092c5761092c612e3e565b9060005260206000209060040201600101540361094f5780915060019250610961565b8061095981612e54565b91505061090e565b5081156109bf57836008828154811061097c5761097c612e3e565b90600052602060002090600402016002018190555082600882815481106109a5576109a5612e3e565b906000526020600020906004020160030181905550610a9b565b604080516080810182526001808252602082018881529282018781526060830187815260088054938401815560005292517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee36004909302928301805460ff191691151591909117905592517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee482015591517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee5830155517ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee6909101555b6040805133815260208101879052908101859052606081018490527ffd30965e9c468e5413ad2a3fa0324386fcf45de8135726765a66c121bf9b09e39060800160405180910390a15050505050565b6000610af582612238565b15610b125760405162461bcd60e51b81526004016106ec90612e6d565b610b1b82611c36565b1515600114610b3c5760405162461bcd60e51b81526004016106ec90612eb5565b6001600160a01b0382166000908152600a60209081526040808320815160e081018352815460ff16151581526001820154938101939093526002810154918301919091526003810154606083015260048101546080830152600581015460a0830181905260069091015460c083015290919081904290610bbf9062015180612dab565b8460800151610bce9190612dc2565b610bd89190612dd5565b11156107e357428260a0015162015180610bf29190612dab565b83608001516107d69190612dc2565b600082815260208190526040902060010154610c1d8133612403565b610c278383612467565b505050565b6002546040516370a0823160e01b815233600482015282916001600160a01b0316906370a0823190602401602060405180830381865afa158015610c74573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610c989190612efd565b1015610cb65760405162461bcd60e51b81526004016106ec90612f16565b610cbf33612238565b15610cdc5760405162461bcd60e51b81526004016106ec90612f5b565b610ce533611c36565b15610d325760405162461bcd60e51b815260206004820181905260248201527f596f75206861766520616c7265616479207374616b6564204653546f6b656e7360448201526064016106ec565b600254610d4a906001600160a01b03163330846124eb565b600354604051630f38ca0d60e31b81526001600160a01b03909116906379c6506890610d7c9033908590600401612f92565b600060405180830381600087803b158015610d9657600080fd5b505af1158015610daa573d6000803e3d6000fd5b505050506000610db982612268565b6040805160e08101825260018082526020808301878152838501868152600680546060870190815242608088019081526004805460a08a019081526005805460c08c01908152336000818152600a909b52998d90209b518c5460ff1916901515178c559751998b0199909955945160028a015591516003890155519087015590519385019390935551929091019190915590519192507f7d9127a72910ce617963edba28318ea738f771668f124319bd636c523b24ac0b9161084d91908590612f92565b6001600160a01b0381163314610eed5760405162461bcd60e51b815260206004820152602f60248201527f416363657373436f6e74726f6c3a2063616e206f6e6c792072656e6f756e636560448201526e103937b632b9903337b91039b2b63360891b60648201526084016106ec565b610ef7828261255c565b5050565b610f0433611c36565b1515600114610f555760405162461bcd60e51b815260206004820152601b60248201527f596f752068617665206e6f204653546f6b656e73207374616b6564000000000060448201526064016106ec565b610f5e336121aa565b15610fab5760405162461bcd60e51b815260206004820152601960248201527f4c6f636b757020706572696f642068617320657870697265640000000000000060448201526064016106ec565b336000818152600a6020908152604091829020825160e081018452815460ff1615158152600182015492810183905260028201548185015260038083015460608301526004808401546080840152600584015460a084015260069093015460c08301525493516370a0823160e01b81529182019490945290916001600160a01b0316906370a0823190602401602060405180830381865afa158015611054573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906110789190612efd565b10156110c65760405162461bcd60e51b815260206004820181905260248201527f596f7520646f6e2774206861766520656e6f7567682073465320746f6b656e2160448201526064016106ec565b6000806064836060015184602001516110df9190612dab565b6110e99190612fab565b90508083602001516110fb9190612dd5565b600254909250611115906001600160a01b031633846125c1565b600754600254611132916001600160a01b039182169116836125c1565b600354602084015160405163079cc67960e41b81526001600160a01b03909216916379cc67909161116891339190600401612f92565b600060405180830381600087803b15801561118257600080fd5b505af1158015611196573d6000803e3d6000fd5b5050336000818152600a6020526040808220805460ff19168155600181018390556002810183905560038101839055600481018390556005810183905560060191909155517fa20e94ac360e12a963d3b1a4111d5d6cebcab4db627c9a6479c6dad34610c7f1935061120c925085908590612e1d565b60405180910390a1505050565b600154604051627eeac760e11b81526000916001600160a01b03169062fdd58e9061124a9033908690600401612f92565b602060405180830381865afa158015611267573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061128b9190612efd565b116112d85760405162461bcd60e51b815260206004820152601760248201527f596f7520646f206e6f74206f776e2074686973204e465400000000000000000060448201526064016106ec565b6112e133612238565b156112fe5760405162461bcd60e51b81526004016106ec90612f5b565b61130733611c36565b156113545760405162461bcd60e51b815260206004820181905260248201527f596f75206861766520616c7265616479207374616b6564204653546f6b656e7360448201526064016106ec565b60018054604051637921219560e11b81526001600160a01b039091169163f242432a9161138991339130918791600401612fcd565b600060405180830381600087803b1580156113a357600080fd5b505af11580156113b7573d6000803e3d6000fd5b5050600154604051634551169d60e01b815260048101859052600093506001600160a01b039091169150634551169d90602401602060405180830381865afa158015611407573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061142b9190612efd565b6040805160c08101825260018082526020808301878152838501868152426060860190815260048054608088019081526005805460a08a019081523360008181526009909952978b902099518a5460ff1916901515178a55955197890197909755925160028801559051600387015590519085015551929091019190915590519192507fae60b3ca24281aea6e75782e0e5a980a7dd9ee173e63fb212a8c0def1fc6efe79161084d91908590612f92565b6001600160a01b0381166000908152600960209081526040808320815160c081018352815460ff1615158152600182810154948201949094526002820154928101929092526003810154606083015260048101546080830181905260059091015460a083015242906115519062015180612dab565b82606001516115609190612dc2565b1061156a57600091505b5092915050565b61157c600033611a8e565b6115985760405162461bcd60e51b81526004016106ec90612de8565b606481106115f95760405162461bcd60e51b815260206004820152602860248201527f596f752063616e6e6f742077697468686f6c64206d6f7265207468616e203939604482015267081c195c98d95b9d60c21b60648201526084016106ec565b600181101561165a5760405162461bcd60e51b815260206004820152602760248201527f596f75206e65656420746f2077697468686f6c64206174206c656173742031206044820152661c195c98d95b9d60ca1b60648201526084016106ec565b60068054908290556040517fbed291e013058f2243e71b2170f425b3c4819b155f012b92e4492b3ad3e866849061084d90339084908690612e1d565b60006116a182612238565b15156001146116f25760405162461bcd60e51b815260206004820181905260248201527f596f7520686176652063757272656e746c79206e6f204e4654207374616b656460448201526064016106ec565b6116fb826114dc565b151560011461171c5760405162461bcd60e51b81526004016106ec90613005565b6001600160a01b038216600090815260096020908152604091829020825160c081018452815460ff16151581526001828101549382019390935260028201549381019390935260038101546060840152600481015460808401526005015460a0830181905290919042906117939062015180612dab565b60808301516117a59062015180612dab565b83606001516117b49190612dc2565b6115609190612dc2565b6117c9600033611a8e565b6117e55760405162461bcd60e51b81526004016106ec90612de8565b60058054908290556040517fdb8d38150b9bb879c12291844bcd9c914b7c4666ae198f4db69a5a5176d13ee89061084d90339084908690612e1d565b6008818154811061183157600080fd5b6000918252602090912060049091020180546001820154600283015460039093015460ff9092169350919084565b61186833612238565b15156001146118b95760405162461bcd60e51b815260206004820181905260248201527f596f7520686176652063757272656e746c79206e6f204e4654207374616b656460448201526064016106ec565b6118c2336114dc565b15156001146118e35760405162461bcd60e51b81526004016106ec90613005565b6118ec33611696565b15156001146119595760405162461bcd60e51b815260206004820152603360248201527f596f75206e65656420746f207761697420666f722074686520636f6f6c20646f604482015272776e20706572696f6420746f2065787069726560681b60648201526084016106ec565b33600081815260096020908152604091829020825160c081018452815460ff161515815260018083015493820184905260028301548286015260038301546060830152600480840154608084015260059093015460a083015280549451637921219560e11b815291956001600160a01b039095169463f242432a946119e49430949293919201612fcd565b600060405180830381600087803b1580156119fe57600080fd5b505af1158015611a12573d6000803e3d6000fd5b5050336000818152600960209081526040808320805460ff19168155600181018490556002810184905560038101849055600481018490556005019290925585015190517fb04b58934e9f7d959ec5e18634b0bc7164b689fa752fd45d2f20f8ccfa33cab19450611a839350612f92565b60405180910390a150565b6000918252602082815260408084206001600160a01b0393909316845291905290205460ff1690565b6000611ac282612238565b15611adf5760405162461bcd60e51b81526004016106ec90612e6d565b611ae882611c36565b1515600114611b095760405162461bcd60e51b81526004016106ec90612eb5565b506001600160a01b03166000908152600a602052604090206001015490565b60606008805480602002602001604051908101604052809291908181526020016000905b82821015611ba55760008481526020908190206040805160808101825260048602909201805460ff1615158352600180820154848601526002820154928401929092526003015460608301529083529092019101611b4c565b50505050905090565b611bb9600033611a8e565b611bd55760405162461bcd60e51b81526004016106ec90612de8565b600180546001600160a01b031981166001600160a01b0384811691821790935560408051338152939092166020840181905291830152907f9d5e5e35ff4b9029875bfd320e82316168739f50ec7d9b2847a08542967036789060600161084d565b6001600160a01b0381166000908152600a6020526040812054819060ff1615156001036106ba5750600192915050565b611c6f33611c36565b1515600114611cc05760405162461bcd60e51b815260206004820152601b60248201527f596f752068617665206e6f204653546f6b656e73207374616b6564000000000060448201526064016106ec565b611cc9336121aa565b1515600114611cea5760405162461bcd60e51b81526004016106ec90613005565b336000818152600a6020908152604091829020825160e081018452815460ff1615158152600182015492810183905260028201548185015260038083015460608301526004808401546080840152600584015460a084015260069093015460c08301525493516370a0823160e01b81529182019490945290916001600160a01b0316906370a0823190602401602060405180830381865afa158015611d93573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611db79190612efd565b1015611e055760405162461bcd60e51b815260206004820181905260248201527f596f7520646f6e2774206861766520656e6f7567682073465320746f6b656e2160448201526064016106ec565b6020810151600254611e24916001600160a01b039091169033906125c1565b600354602082015160405163079cc67960e41b81526001600160a01b03909216916379cc679091611e5a91339190600401612f92565b600060405180830381600087803b158015611e7457600080fd5b505af1158015611e88573d6000803e3d6000fd5b5050336000818152600a60209081526040808320805460ff1916815560018101849055600281018490556003810184905560048101849055600581018490556006019290925585015190517e0394400365c07f75e43823dbaaeed7ca6913196a36451c4a64bf7a09e6de8e9450611a839350612f92565b600082815260208190526040902060010154611f1b8133612403565b610c27838361255c565b6000611f3082612238565b1515600114611f515760405162461bcd60e51b81526004016106ec90612d0b565b611f5a82611c36565b15611f775760405162461bcd60e51b81526004016106ec90612d4d565b506001600160a01b031660009081526009602052604090206001015490565b6002546040516370a0823160e01b815233600482015282916001600160a01b0316906370a0823190602401602060405180830381865afa158015611fde573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906120029190612efd565b10156120205760405162461bcd60e51b81526004016106ec90612f16565b61202933612238565b156120465760405162461bcd60e51b81526004016106ec90612f5b565b61204f33611c36565b15156001146120a05760405162461bcd60e51b815260206004820152601f60248201527f596f7520646f206e6f742068617665207374616b6564204653546f6b656e730060448201526064016106ec565b6002546120b8906001600160a01b03163330846124eb565b600354604051630f38ca0d60e31b81526001600160a01b03909116906379c65068906120ea9033908590600401612f92565b600060405180830381600087803b15801561210457600080fd5b505af1158015612118573d6000803e3d6000fd5b5050336000908152600a602052604090206001015461213a9250839150612dc2565b336000908152600a602052604081206001018290559061215990612268565b336000818152600a6020526040908190206002810184905542600490910155519192507f7d9127a72910ce617963edba28318ea738f771668f124319bd636c523b24ac0b9161084d91908590612f92565b6001600160a01b0381166000908152600a60209081526040808320815160e081018352815460ff1615158152600182810154948201949094526002820154928101929092526003810154606083015260048101546080830152600581015460a0830181905260069091015460c083015242906122299062015180612dab565b82608001516115609190612dc2565b6001600160a01b038116600090815260096020526040812054819060ff1615156001036106ba5750600192915050565b600080805b60085481101561156a576008818154811061228a5761228a612e3e565b90600052602060002090600402016002015484101580156122cf5750600881815481106122b9576122b9612e3e565b9060005260206000209060040201600301548411155b1561230057600881815481106122e7576122e7612e3e565b906000526020600020906004020160010154915061156a565b8061230a81612e54565b91505061226d565b60008061231e83612238565b156123a3576001546001600160a01b0316634551169d61233d85611f25565b6040518263ffffffff1660e01b815260040161235b91815260200190565b602060405180830381865afa158015612378573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061239c9190612efd565b90506106ba565b6123ac83611c36565b156106ba576001600160a01b0383166000908152600a60205260409020600101546123d681612268565b949350505050565b60006001600160e01b03198216637965db0b60e01b14806106ba57506106ba826125e0565b61240d8282611a8e565b610ef757612425816001600160a01b03166014612615565b612430836020612615565b604051602001612441929190613060565b60408051601f198184030181529082905262461bcd60e51b82526106ec916004016130d5565b6124718282611a8e565b610ef7576000828152602081815260408083206001600160a01b03851684529091529020805460ff191660011790556124a73390565b6001600160a01b0316816001600160a01b0316837f2f8788117e7eff1d82e926ec794901d17c78024a50270940304540a733656f0d60405160405180910390a45050565b6040516001600160a01b03808516602483015283166044820152606481018290526125569085906323b872dd60e01b906084015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b0319909316929092179091526127b1565b50505050565b6125668282611a8e565b15610ef7576000828152602081815260408083206001600160a01b0385168085529252808320805460ff1916905551339285917ff6391f5c32d9c69d2a47ea670b442974b53935d1edc7fd64eb21e047a839171b9190a45050565b610c278363a9059cbb60e01b848460405160240161251f929190612f92565b60006001600160e01b03198216630271189760e51b14806106ba57506301ffc9a760e01b6001600160e01b03198316146106ba565b60606000612624836002612dab565b61262f906002612dc2565b67ffffffffffffffff81111561264757612647612ac8565b6040519080825280601f01601f191660200182016040528015612671576020820181803683370190505b509050600360fc1b8160008151811061268c5761268c612e3e565b60200101906001600160f81b031916908160001a905350600f60fb1b816001815181106126bb576126bb612e3e565b60200101906001600160f81b031916908160001a90535060006126df846002612dab565b6126ea906001612dc2565b90505b6001811115612762576f181899199a1a9b1b9c1cb0b131b232b360811b85600f166010811061271e5761271e612e3e565b1a60f81b82828151811061273457612734612e3e565b60200101906001600160f81b031916908160001a90535060049490941c9361275b81613108565b90506126ed565b5083156107e35760405162461bcd60e51b815260206004820181905260248201527f537472696e67733a20686578206c656e67746820696e73756666696369656e7460448201526064016106ec565b6000612806826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166128839092919063ffffffff16565b805190915015610c275780806020019051810190612824919061311f565b610c275760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b60648201526084016106ec565b60606107e0848460008585843b6128dc5760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e747261637400000060448201526064016106ec565b600080866001600160a01b031685876040516128f89190613141565b60006040518083038185875af1925050503d8060008114612935576040519150601f19603f3d011682016040523d82523d6000602084013e61293a565b606091505b509150915061294a828286612955565b979650505050505050565b606083156129645750816107e3565b8251156129745782518084602001fd5b8160405162461bcd60e51b81526004016106ec91906130d5565b6000602082840312156129a057600080fd5b81356001600160e01b0319811681146107e357600080fd5b6001600160a01b03811681146129cd57600080fd5b50565b6000602082840312156129e257600080fd5b81356107e3816129b8565b6000602082840312156129ff57600080fd5b5035919050565b600080600060608486031215612a1b57600080fd5b505081359360208301359350604090920135919050565b60008060408385031215612a4557600080fd5b823591506020830135612a57816129b8565b809150509250929050565b602080825282518282018190526000919060409081850190868401855b82811015612abb578151805115158552868101518786015285810151868601526060908101519085015260809093019290850190600101612a7f565b5091979650505050505050565b634e487b7160e01b600052604160045260246000fd5b604051601f8201601f1916810167ffffffffffffffff81118282101715612b0757612b07612ac8565b604052919050565b600082601f830112612b2057600080fd5b8135602067ffffffffffffffff821115612b3c57612b3c612ac8565b8160051b612b4b828201612ade565b9283528481018201928281019087851115612b6557600080fd5b83870192505b8483101561294a57823582529183019190830190612b6b565b600082601f830112612b9557600080fd5b813567ffffffffffffffff811115612baf57612baf612ac8565b612bc2601f8201601f1916602001612ade565b818152846020838601011115612bd757600080fd5b816020850160208301376000918101602001919091529392505050565b600080600080600060a08688031215612c0c57600080fd5b8535612c17816129b8565b94506020860135612c27816129b8565b9350604086013567ffffffffffffffff80821115612c4457600080fd5b612c5089838a01612b0f565b94506060880135915080821115612c6657600080fd5b612c7289838a01612b0f565b93506080880135915080821115612c8857600080fd5b50612c9588828901612b84565b9150509295509295909350565b600080600080600060a08688031215612cba57600080fd5b8535612cc5816129b8565b94506020860135612cd5816129b8565b93506040860135925060608601359150608086013567ffffffffffffffff811115612cff57600080fd5b612c9588828901612b84565b60208082526022908201527f57616c6c6574206861732063757272656e746c79206e6f204e4654207374616b604082015261195960f21b606082015260800190565b60208082526028908201527f57616c6c657420686173207374616b656420465320546f6b656e7320616e64206040820152676e6f74204e46547360c01b606082015260800190565b634e487b7160e01b600052601160045260246000fd5b80820281158282048414176106ba576106ba612d95565b808201808211156106ba576106ba612d95565b818103818111156106ba576106ba612d95565b6020808252818101527f4163636f756e74206973206e6f7420696e207468652061646d696e206c697374604082015260600190565b6001600160a01b039390931683526020830191909152604082015260600190565b634e487b7160e01b600052603260045260246000fd5b600060018201612e6657612e66612d95565b5060010190565b60208082526028908201527f57616c6c657420686173207374616b6564204e46547320616e64206e6f7420466040820152675320746f6b656e7360c01b606082015260800190565b60208082526028908201527f57616c6c6574206861732063757272656e746c79206e6f20465320546f6b656e6040820152671cc81cdd185ad95960c21b606082015260800190565b600060208284031215612f0f57600080fd5b5051919050565b60208082526025908201527f596f7520646f206e6f74206f776e20656e6f75676820746f6b656e7320746f206040820152647374616b6560d81b606082015260800190565b6020808252601c908201527f596f75206861766520616c7265616479207374616b6564204e46547300000000604082015260600190565b6001600160a01b03929092168252602082015260400190565b600082612fc857634e487b7160e01b600052601260045260246000fd5b500490565b6001600160a01b0394851681529290931660208301526040820152606081019190915260a06080820181905260009082015260c00190565b6020808252601b908201527f4c6f636b757020706572696f64207374696c6c2070656e64696e670000000000604082015260600190565b60005b8381101561305757818101518382015260200161303f565b50506000910152565b7f416363657373436f6e74726f6c3a206163636f756e742000000000000000000081526000835161309881601785016020880161303c565b7001034b99036b4b9b9b4b733903937b6329607d1b60179184019182015283516130c981602884016020880161303c565b01602801949350505050565b60208152600082518060208401526130f481604085016020870161303c565b601f01601f19169190910160400192915050565b60008161311757613117612d95565b506000190190565b60006020828403121561313157600080fd5b815180151581146107e357600080fd5b6000825161315381846020870161303c565b919091019291505056fea264697066735822122067d4062d6fc8607b22438ab1050c07400873052d52dc01ccb20934a8a5b1e69564736f6c63430008120033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
0000000000000000000000004db1e329713f3b4d606f3d3956eed3eca7dc6e99000000000000000000000000bc0d0650412ef353d672c0bbd12efff90591b251000000000000000000000000a81b289dc053c242b43aed38f2b77e30dd459ec10000000000000000000000006e2a0a942eaa01b7eb2639b8b65d1d2768a87bac
-----Decoded View---------------
Arg [0] : _tierFactory (address): 0x4db1e329713F3b4d606f3D3956Eed3EcA7dc6E99
Arg [1] : _fsToken (address): 0xBC0d0650412EF353D672c0Bbd12eFFF90591B251
Arg [2] : _sFSToken (address): 0xa81b289dc053c242B43aed38F2B77E30dd459Ec1
Arg [3] : _devWallet (address): 0x6E2A0A942Eaa01B7EB2639B8B65D1D2768a87BAc
-----Encoded View---------------
4 Constructor Arguments found :
Arg [0] : 0000000000000000000000004db1e329713f3b4d606f3d3956eed3eca7dc6e99
Arg [1] : 000000000000000000000000bc0d0650412ef353d672c0bbd12efff90591b251
Arg [2] : 000000000000000000000000a81b289dc053c242b43aed38f2b77e30dd459ec1
Arg [3] : 0000000000000000000000006e2a0a942eaa01b7eb2639b8b65d1d2768a87bac
Deployed Bytecode Sourcemap
45355:25007:0:-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;45772:31;;;;;;;;;160:25:1;;;148:2;133:18;45772:31:0;;;;;;;;49065:253;;;;;;:::i;:::-;;:::i;:::-;;;652:14:1;;645:22;627:41;;615:2;600:18;49065:253:0;487:187:1;55708:938:0;;;;;;:::i;:::-;;:::i;51391:208::-;;;;;;:::i;:::-;;:::i;:::-;;51968:231;;;;;;:::i;:::-;;:::i;49433:1159::-;;;;;;:::i;:::-;;:::i;25726:123::-;;;;;;:::i;:::-;25792:7;25819:12;;;;;;;;;;:22;;;;25726:123;56756:966;;;;;;:::i;:::-;;:::i;26111:172::-;;;;;;:::i;:::-;;:::i;62734:1417::-;;;;;;:::i;:::-;;:::i;27209:280::-;;;;;;:::i;:::-;;:::i;68568:1791::-;;;:::i;61523:1053::-;;;;;;:::i;:::-;;:::i;57833:737::-;;;;;;:::i;:::-;;:::i;47098:67::-;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;2566:14:1;;2559:22;2541:41;;2613:2;2598:18;;2591:34;;;;2641:18;;;2634:34;;;;2699:2;2684:18;;2677:34;2742:3;2727:19;;2720:35;2786:3;2771:19;;2764:35;2528:3;2513:19;47098:67:0;2260:545:1;52281:715:0;;;;;;:::i;:::-;;:::i;45892:47::-;;;;;;60293:1060;;;;;;:::i;:::-;;:::i;51685:220::-;;;;;;:::i;:::-;;:::i;45532:21::-;;;;;-1:-1:-1;;;;;45532:21:0;;;;;;-1:-1:-1;;;;;2989:32:1;;;2971:51;;2959:2;2944:18;45532:21:0;2810:218:1;46973:38:0;;;;;;:::i;:::-;;:::i;:::-;;;;3283:14:1;;3276:22;3258:41;;3330:2;3315:18;;3308:34;;;;3358:18;;;3351:34;3416:2;3401:18;;3394:34;3245:3;3230:19;46973:38:0;3033:401:1;45488:37:0;;;;;-1:-1:-1;;;;;45488:37:0;;;65867:1201;;;:::i;24586:164::-;;;;;;:::i;:::-;;:::i;53618:487::-;;;;;;:::i;:::-;;:::i;50687:158::-;;;:::i;:::-;;;;;;;:::i;45666:29::-;;;;;;22239:49;;22284:4;22239:49;;50955:351;;;;;;:::i;:::-;;:::i;59902:305::-;;;;;;:::i;:::-;;:::i;45560:22::-;;;;;-1:-1:-1;;;;;45560:22:0;;;39797:255;;;;;;:::i;:::-;-1:-1:-1;;;39797:255:0;;;;;;;;;;;-1:-1:-1;;;;;;7809:33:1;;;7791:52;;7779:2;7764:18;39797:255:0;7647:202:1;67145:1332:0;;;:::i;47172:75::-;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;8188:14:1;;8181:22;8163:41;;8235:2;8220:18;;8213:34;;;;8263:18;;;8256:34;;;;8321:2;8306:18;;8299:34;;;;8364:3;8349:19;;8342:35;8408:3;8393:19;;8386:35;8452:3;8437:19;;8430:35;8150:3;8135:19;47172:75:0;7854:617:1;26528:174:0;;;;;;:::i;:::-;;:::i;53080:458::-;;;;;;:::i;:::-;;:::i;64227:1550::-;;;;;;:::i;:::-;;:::i;58671:756::-;;;;;;:::i;:::-;;:::i;59524:291::-;;;;;;:::i;:::-;;:::i;55087:515::-;;;;;;:::i;:::-;;:::i;54234:761::-;;;;;;:::i;:::-;;:::i;39562:227::-;;;;;;:::i;:::-;-1:-1:-1;;;39562:227:0;;;;;;;;49065:253;49244:4;49273:37;49297:12;49273:23;:37::i;:::-;49266:44;49065:253;-1:-1:-1;;49065:253:0:o;55708:938::-;55798:22;55855:36;55883:7;55855:27;:36::i;:::-;:44;;55895:4;55855:44;55833:128;;;;-1:-1:-1;;;55833:128:0;;;;;;;:::i;:::-;;;;;;;;;55994:41;56027:7;55994:32;:41::i;:::-;:50;55972:140;;;;-1:-1:-1;;;55972:140:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;56163:59:0;;56125:35;56163:59;;;:26;:59;;;;;;;;56125:97;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:35;;;56398:15;;56336:41;;56371:6;56336:41;:::i;:::-;56283:14;:32;;;:95;;;;:::i;:::-;:130;;;;:::i;:::-;56282:136;56264:349;;;56586:15;56524:14;:32;;;56559:6;56524:41;;;;:::i;:::-;56471:14;:32;;;:95;;;;:::i;:::-;:130;;;;:::i;:::-;56445:156;;56264:349;56632:6;55708:938;-1:-1:-1;;;55708:938:0:o;51391:208::-;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;51480:10:::1;::::0;;51503:18;;;;51539:52:::1;::::0;::::1;::::0;::::1;::::0;51557:10:::1;::::0;51480;;51516:5;;51539:52:::1;:::i;:::-;;;;;;;;51444:155;51391:208:::0;:::o;51968:231::-;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;52067:9:::1;::::0;;-1:-1:-1;;;;;;52089:22:0;::::1;-1:-1:-1::0;;;;;52089:22:0;;::::1;::::0;;::::1;::::0;;;52129:62:::1;::::0;;52153:10:::1;11546:34:1::0;;52067:9:0;;;::::1;11611:2:1::0;11596:18;;11589:43;;;11648:18;;;11641:43;52067:9:0;52129:62:::1;::::0;11496:2:1;11481:18;52129:62:0::1;11306:384:1::0;49433:1159:0;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;49672:16:::1;49707:18:::0;49747:9:::1;49742:233;49766:16;:23:::0;49762:27;::::1;49742:233;;;49845:7;49815:16;49832:1;49815:19;;;;;;;;:::i;:::-;;;;;;;;;;;:26;;;:37:::0;49811:153:::1;;49886:1;49873:14;;49920:4;49906:18;;49943:5;;49811:153;49791:3:::0;::::1;::::0;::::1;:::i;:::-;;;;49742:233;;;;49991:11;49987:438;;;50128:12;50085:16;50102:10;50085:28;;;;;;;;:::i;:::-;;;;;;;;;;;:40;;:55;;;;50198:12;50155:16;50172:10;50155:28;;;;;;;;:::i;:::-;;;;;;;;;;;:40;;:55;;;;49987:438;;;50343:55;::::0;;::::1;::::0;::::1;::::0;;50356:4:::1;50343:55:::0;;;::::1;::::0;::::1;::::0;;;;;;;;;;;;;;;50303:16:::1;:110:::0;;;;::::1;::::0;;-1:-1:-1;50303:110:0;;;;::::1;::::0;;::::1;::::0;;::::1;::::0;;-1:-1:-1;;50303:110:0::1;::::0;::::1;;::::0;;;::::1;::::0;;;;;;;;;;;;;;;;;;;;49987:438:::1;50442:142;::::0;;50487:10:::1;12198:51:1::0;;12280:2;12265:18;;12258:34;;;12308:18;;;12301:34;;;12366:2;12351:18;;12344:34;;;50442:142:0::1;::::0;12185:3:1;12170:19;50442:142:0::1;;;;;;;49572:1020;;49433:1159:::0;;;:::o;56756:966::-;56851:22;56908:36;56936:7;56908:27;:36::i;:::-;:45;56886:135;;;;-1:-1:-1;;;56886:135:0;;;;;;;:::i;:::-;57054:41;57087:7;57054:32;:41::i;:::-;:49;;57099:4;57054:49;57032:139;;;;-1:-1:-1;;;57032:139:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;57243:39:0;;57184:56;57243:39;;;:30;:39;;;;;;;;57184:98;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:56;;;57466:15;;57400:45;;57439:6;57400:45;:::i;:::-;57343:18;:36;;;:103;;;;:::i;:::-;:138;;;;:::i;:::-;57342:144;57324:365;;;57662:15;57596:18;:36;;;57635:6;57596:45;;;;:::i;:::-;57539:18;:36;;;:103;;;;:::i;26111:172::-;25792:7;25819:12;;;;;;;;;;:22;;;23945:30;23956:4;683:10;23945;:30::i;:::-;26250:25:::1;26261:4;26267:7;26250:10;:25::i;:::-;26111:172:::0;;;:::o;62734:1417::-;62832:7;;:29;;-1:-1:-1;;;62832:29:0;;62850:10;62832:29;;;2971:51:1;62865:21:0;;-1:-1:-1;;;;;62832:7:0;;:17;;2944:18:1;;62832:29:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:54;;62810:141;;;;-1:-1:-1;;;62810:141:0;;;;;;;:::i;:::-;62984:39;63012:10;62984:27;:39::i;:::-;:48;62962:126;;;;-1:-1:-1;;;62962:126:0;;;;;;;:::i;:::-;63121:44;63154:10;63121:32;:44::i;:::-;:53;63099:135;;;;-1:-1:-1;;;63099:135:0;;14569:2:1;63099:135:0;;;14551:21:1;;;14588:18;;;14581:30;14647:34;14627:18;;;14620:62;14699:18;;63099:135:0;14367:356:1;63099:135:0;63316:7;;:124;;-1:-1:-1;;;;;63316:7:0;63355:10;63388:4;63408:21;63316:24;:124::i;:::-;63481:8;;:53;;-1:-1:-1;;;63481:53:0;;-1:-1:-1;;;;;63481:8:0;;;;:18;;:53;;63500:10;;63512:21;;63481:53;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;63616:15;63634:48;63660:21;63634:25;:48::i;:::-;63816:229;;;;;;;;63848:4;63816:229;;;;;;;;;;;;;;;;63925:27;;;63816:229;;;;;;63967:15;63816:229;;;;;;63997:10;;;63816:229;;;;;;64022:12;;;63816:229;;;;;;63802:10;-1:-1:-1;63771:42:0;;;:30;:42;;;;;;;:274;;;;-1:-1:-1;;63771:274:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;64086:57;;63816:229;;-1:-1:-1;64086:57:0;;;;63802:10;63816:229;;64086:57;:::i;27209:280::-;-1:-1:-1;;;;;27344:23:0;;683:10;27344:23;27322:120;;;;-1:-1:-1;;;27322:120:0;;15209:2:1;27322:120:0;;;15191:21:1;15248:2;15228:18;;;15221:30;15287:34;15267:18;;;15260:62;-1:-1:-1;;;15338:18:1;;;15331:45;15393:19;;27322:120:0;15007:411:1;27322:120:0;27455:26;27467:4;27473:7;27455:11;:26::i;:::-;27209:280;;:::o;68568:1791::-;68657:44;68690:10;68657:32;:44::i;:::-;:52;;68705:4;68657:52;68635:129;;;;-1:-1:-1;;;68635:129:0;;15625:2:1;68635:129:0;;;15607:21:1;15664:2;15644:18;;;15637:30;15703:29;15683:18;;;15676:57;15750:18;;68635:129:0;15423:351:1;68635:129:0;68797:45;68831:10;68797:33;:45::i;:::-;:54;68775:129;;;;-1:-1:-1;;;68775:129:0;;15981:2:1;68775:129:0;;;15963:21:1;16020:2;16000:18;;;15993:30;16059:27;16039:18;;;16032:55;16104:18;;68775:129:0;15779:349:1;68775:129:0;69066:10;68958:56;69017:74;;;:30;:74;;;;;;;;;68958:133;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;69126:8;:30;;-1:-1:-1;;;69126:30:0;;;;;2971:51:1;;;;68958:133:0;;-1:-1:-1;;;;;69126:8:0;;:18;;2944::1;;69126:30:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:64;;69104:146;;;;-1:-1:-1;;;69104:146:0;;16335:2:1;69104:146:0;;;16317:21:1;;;16354:18;;;16347:30;16413:34;16393:18;;;16386:62;16465:18;;69104:146:0;16133:356:1;69104:146:0;69263:33;69311:35;69575:3;69512:18;:46;;;69462:18;:30;;;:96;;;;:::i;:::-;69461:117;;;;:::i;:::-;69418:160;;69676:27;69630:18;:30;;;:73;;;;:::i;:::-;69789:7;;69589:114;;-1:-1:-1;69789:59:0;;-1:-1:-1;;;;;69789:7:0;69810:10;69589:114;69789:20;:59::i;:::-;69880:9;;69859:7;;:60;;-1:-1:-1;;;;;69859:7:0;;;;69880:9;69891:27;69859:20;:60::i;:::-;69968:8;;69998:30;;;;69968:61;;-1:-1:-1;;;69968:61:0;;-1:-1:-1;;;;;69968:8:0;;;;:17;;:61;;69986:10;;69998:30;69968:61;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;70148:10:0;70117:42;;;;:30;:42;;;;;;70110:49;;-1:-1:-1;;70110:49:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;70200:151;;;-1:-1:-1;70200:151:0;;-1:-1:-1;70273:25:0;;70313:27;;70200:151;:::i;:::-;;;;;;;;68624:1735;;;68568:1791::o;61523:1053::-;61601:11;;:41;;-1:-1:-1;;;61601:41:0;;61645:1;;-1:-1:-1;;;;;61601:11:0;;:21;;:41;;61623:10;;61635:6;;61601:41;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:45;61579:118;;;;-1:-1:-1;;;61579:118:0;;16918:2:1;61579:118:0;;;16900:21:1;16957:2;16937:18;;;16930:30;16996:25;16976:18;;;16969:53;17039:18;;61579:118:0;16716:347:1;61579:118:0;61730:39;61758:10;61730:27;:39::i;:::-;:48;61708:126;;;;-1:-1:-1;;;61708:126:0;;;;;;;:::i;:::-;61867:44;61900:10;61867:32;:44::i;:::-;:53;61845:135;;;;-1:-1:-1;;;61845:135:0;;14569:2:1;61845:135:0;;;14551:21:1;;;14588:18;;;14581:30;14647:34;14627:18;;;14620:62;14699:18;;61845:135:0;14367:356:1;61845:135:0;62062:11;;;:70;;-1:-1:-1;;;62062:70:0;;-1:-1:-1;;;;;62062:11:0;;;;:28;;:70;;62091:10;;62111:4;;62118:6;;62062:70;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;62235:11:0;;:34;;-1:-1:-1;;;62235:34:0;;;;;160:25:1;;;62217:15:0;;-1:-1:-1;;;;;;62235:11:0;;;;-1:-1:-1;62235:26:0;;133:18:1;;62235:34:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;62321:168;;;;;;;;62349:4;62321:168;;;;;;;;;;;;;;;;62411:15;62321:168;;;;;;62441:10;;;62321:168;;;;;;62466:12;;;62321:168;;;;;;62307:10;-1:-1:-1;62280:38:0;;;:26;:38;;;;;;;:209;;;;-1:-1:-1;;62280:209:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;62530:38;;62321:168;;-1:-1:-1;62530:38:0;;;;62307:10;62321:168;;62530:38;:::i;57833:737::-;-1:-1:-1;;;;;58075:59:0;;57925:27;58075:59;;;:26;:59;;;;;;;;58037:97;;;;;;;;;;;;;;;57979:4;58037:97;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;58469:15;;58394:58;;58446:6;58394:58;:::i;:::-;58342:14;:32;;;:110;;;;:::i;:::-;:142;58324:213;;58520:5;58511:14;;58324:213;-1:-1:-1;58556:6:0;57833:737;-1:-1:-1;;57833:737:0:o;52281:715::-;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;52454:3:::1;52423:28;:34;52401:124;;;::::0;-1:-1:-1;;;52401:124:0;;17910:2:1;52401:124:0::1;::::0;::::1;17892:21:1::0;17949:2;17929:18;;;17922:30;17988:34;17968:18;;;17961:62;-1:-1:-1;;;18039:18:1;;;18032:38;18087:19;;52401:124:0::1;17708:404:1::0;52401:124:0::1;52590:1;52558:28;:33;;52536:122;;;::::0;-1:-1:-1;;;52536:122:0;;18319:2:1;52536:122:0::1;::::0;::::1;18301:21:1::0;18358:2;18338:18;;;18331:30;18397:34;18377:18;;;18370:62;-1:-1:-1;;;18448:18:1;;;18441:37;18495:19;;52536:122:0::1;18117:403:1::0;52536:122:0::1;52713:27;::::0;;52753:58;;;;52829:159:::1;::::0;::::1;::::0;::::1;::::0;52878:10:::1;::::0;52713:27;;52783:28;;52829:159:::1;:::i;60293:1060::-:0;60397:12;60444:36;60472:7;60444:27;:36::i;:::-;:44;;60484:4;60444:44;60422:126;;;;-1:-1:-1;;;60422:126:0;;18727:2:1;60422:126:0;;;18709:21:1;;;18746:18;;;18739:30;18805:34;18785:18;;;18778:62;18857:18;;60422:126:0;18525:356:1;60422:126:0;60581:37;60610:7;60581:28;:37::i;:::-;:45;;60622:4;60581:45;60559:122;;;;-1:-1:-1;;;60559:122:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;60804:59:0;;60694:11;60804:59;;;:26;:59;;;;;;;;;60766:97;;;;;;;;;;;;;;;60708:4;60766:97;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;60708:4;;60766:97;61252:15;;61184:50;;61228:6;61184:50;:::i;:::-;61121:32;;;;:41;;61156:6;61121:41;:::i;:::-;61068:14;:32;;;:95;;;;:::i;:::-;:167;;;;:::i;51685:220::-;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;51778:12:::1;::::0;;51803:20;;;;51841:56:::1;::::0;::::1;::::0;::::1;::::0;51861:10:::1;::::0;51778:12;;51818:5;;51841:56:::1;:::i;46973:38::-:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;46973:38:0;;;:::o;65867:1201::-;65933:39;65961:10;65933:27;:39::i;:::-;:47;;65976:4;65933:47;65911:129;;;;-1:-1:-1;;;65911:129:0;;18727:2:1;65911:129:0;;;18709:21:1;;;18746:18;;;18739:30;18805:34;18785:18;;;18778:62;18857:18;;65911:129:0;18525:356:1;65911:129:0;66073:40;66102:10;66073:28;:40::i;:::-;:48;;66117:4;66073:48;66051:125;;;;-1:-1:-1;;;66051:125:0;;;;;;;:::i;:::-;66209:52;66250:10;66209:40;:52::i;:::-;:60;;66265:4;66209:60;66187:161;;;;-1:-1:-1;;;66187:161:0;;19444:2:1;66187:161:0;;;19426:21:1;19483:2;19463:18;;;19456:30;19522:34;19502:18;;;19495:62;-1:-1:-1;;;19573:18:1;;;19566:49;19632:19;;66187:161:0;19242:415:1;66187:161:0;66481:10;66402:35;66440:62;;;:26;:62;;;;;;;;;66402:100;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;66679:11;;:160;;-1:-1:-1;;;66679:160:0;;66402:100;;-1:-1:-1;;;;;66679:11:0;;;;:28;;:160;;66730:4;;66481:10;;66402:100;;66679:160;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;66950:10:0;66923:38;;;;:26;:38;;;;;;;;66916:45;;-1:-1:-1;;66916:45:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;67039:20;;;67002:58;;;;-1:-1:-1;67002:58:0;;-1:-1:-1;67002:58:0;:::i;:::-;;;;;;;;65900:1168;65867:1201::o;24586:164::-;24689:4;24713:12;;;;;;;;;;;-1:-1:-1;;;;;24713:29:0;;;;;;;;;;;;;;;24586:164::o;53618:487::-;53703:25;53763:36;53791:7;53763:27;:36::i;:::-;:45;53741:135;;;;-1:-1:-1;;;53741:135:0;;;;;;;:::i;:::-;53909:41;53942:7;53909:32;:41::i;:::-;:49;;53954:4;53909:49;53887:139;;;;-1:-1:-1;;;53887:139:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;;54046:39:0;;;;;:30;:39;;;;;:51;;;;53618:487::o;50687:158::-;50762:34;50821:16;50814:23;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;50687:158;:::o;50955:351::-;24055:41;22284:4;683:10;24586:164;:::i;24055:41::-;24033:123;;;;-1:-1:-1;;;24033:123:0;;;;;;;:::i;:::-;51105:11:::1;::::0;;-1:-1:-1;;;;;;51129:26:0;::::1;-1:-1:-1::0;;;;;51129:26:0;;::::1;::::0;;::::1;::::0;;;51173:125:::1;::::0;;51213:10:::1;11546:34:1::0;;51105:11:0;;;::::1;11611:2:1::0;11596:18;;11589:43;;;11648:18;;;11641:43;51105:11:0;51173:125:::1;::::0;11496:2:1;11481:18;51173:125:0::1;11306:384:1::0;59902:305:0;-1:-1:-1;;;;;60069:39:0;;59998:22;60069:39;;;:30;:39;;;;;:55;59998:22;;60069:55;;:63;;:55;:63;60065:109;;-1:-1:-1;60158:4:0;60193:6;59902:305;-1:-1:-1;;59902:305:0:o;67145:1332::-;67233:44;67266:10;67233:32;:44::i;:::-;:52;;67281:4;67233:52;67211:129;;;;-1:-1:-1;;;67211:129:0;;15625:2:1;67211:129:0;;;15607:21:1;15664:2;15644:18;;;15637:30;15703:29;15683:18;;;15676:57;15750:18;;67211:129:0;15423:351:1;67211:129:0;67373:45;67407:10;67373:33;:45::i;:::-;:53;;67422:4;67373:53;67351:130;;;;-1:-1:-1;;;67351:130:0;;;;;;;:::i;:::-;67643:10;67535:56;67594:74;;;:30;:74;;;;;;;;;67535:133;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;67703:8;:30;;-1:-1:-1;;;67703:30:0;;;;;2971:51:1;;;;67535:133:0;;-1:-1:-1;;;;;67703:8:0;;:18;;2944::1;;67703:30:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:64;;67681:146;;;;-1:-1:-1;;;67681:146:0;;16335:2:1;67681:146:0;;;16317:21:1;;;16354:18;;;16347:30;16413:34;16393:18;;;16386:62;16465:18;;67681:146:0;16133:356:1;67681:146:0;68048:30;;;;68015:7;;:64;;-1:-1:-1;;;;;68015:7:0;;;;68036:10;;68015:20;:64::i;:::-;68128:8;;68158:30;;;;68128:61;;-1:-1:-1;;;68128:61:0;;-1:-1:-1;;;;;68128:8:0;;;;:17;;:61;;68146:10;;68158:30;68128:61;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;68308:10:0;68277:42;;;;:30;:42;;;;;;;;68270:49;;-1:-1:-1;;68270:49:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;68428:30;;;68360:109;;;;-1:-1:-1;68360:109:0;;-1:-1:-1;68360:109:0;:::i;26528:174::-;25792:7;25819:12;;;;;;;;;;:22;;;23945:30;23956:4;683:10;23945;:30::i;:::-;26668:26:::1;26680:4;26686:7;26668:11;:26::i;53080:458::-:0;53158:19;53212:36;53240:7;53212:27;:36::i;:::-;:44;;53252:4;53212:44;53190:128;;;;-1:-1:-1;;;53190:128:0;;;;;;;:::i;:::-;53351:41;53384:7;53351:32;:41::i;:::-;:50;53329:140;;;;-1:-1:-1;;;53329:140:0;;;;;;;:::i;:::-;-1:-1:-1;;;;;;53489:35:0;;;;;:26;:35;;;;;:41;;;;53080:458::o;64227:1550::-;64335:7;;:29;;-1:-1:-1;;;64335:29:0;;64353:10;64335:29;;;2971:51:1;64368:21:0;;-1:-1:-1;;;;;64335:7:0;;:17;;2944:18:1;;64335:29:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;:54;;64313:141;;;;-1:-1:-1;;;64313:141:0;;;;;;;:::i;:::-;64487:39;64515:10;64487:27;:39::i;:::-;:48;64465:126;;;;-1:-1:-1;;;64465:126:0;;;;;;;:::i;:::-;64624:44;64657:10;64624:32;:44::i;:::-;:52;;64672:4;64624:52;64602:133;;;;-1:-1:-1;;;64602:133:0;;20307:2:1;64602:133:0;;;20289:21:1;20346:2;20326:18;;;20319:30;20385:33;20365:18;;;20358:61;20436:18;;64602:133:0;20105:355:1;64602:133:0;64817:7;;:124;;-1:-1:-1;;;;;64817:7:0;64856:10;64889:4;64909:21;64817:24;:124::i;:::-;64982:8;;:53;;-1:-1:-1;;;64982:53:0;;-1:-1:-1;;;;;64982:8:0;;;;:18;;:53;;65001:10;;65013:21;;64982:53;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;;65225:10:0;65194:42;;;;:30;:42;;;;;:54;;;:91;;-1:-1:-1;65264:21:0;;-1:-1:-1;65194:91:0;:::i;:::-;65155:10;65124:42;;;;:30;:42;;;;;:54;;:161;;;:42;65347:105;;:25;:105::i;:::-;65494:10;65463:42;;;;:30;:42;;;;;;;:49;;;:59;;;65642:29;65579:60;;;;:92;65712:57;65329:123;;-1:-1:-1;65712:57:0;;;;65494:10;65747:21;;65712:57;:::i;58671:756::-;-1:-1:-1;;;;;58944:39:0;;58768:32;58944:39;;;:30;:39;;;;;;;;58885:98;;;;;;;;;;;;;;;58827:4;58885:98;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;59326:15;;59247:62;;59303:6;59247:62;:::i;:::-;59191:18;:36;;;:118;;;;:::i;59524:291::-;-1:-1:-1;;;;;59681:35:0;;59615:17;59681:35;;;:26;:35;;;;;:51;59615:17;;59681:51;;:59;;:51;:59;59677:105;;-1:-1:-1;59766:4:0;59801:6;59524:291;-1:-1:-1;;59524:291:0:o;55087:515::-;55182:14;;;55240:329;55264:16;:23;55260:27;;55240:329;;;55348:16;55365:1;55348:19;;;;;;;;:::i;:::-;;;;;;;;;;;:31;;;55331:13;:48;;:117;;;;;55417:16;55434:1;55417:19;;;;;;;;:::i;:::-;;;;;;;;;;;:31;;;55400:13;:48;;55331:117;55309:249;;;55492:16;55509:1;55492:19;;;;;;;;:::i;:::-;;;;;;;;;;;:26;;;55483:35;;55537:5;;55309:249;55289:3;;;;:::i;:::-;;;;55240:329;;54234:761;54321:14;;54383:36;54411:7;54383:27;:36::i;:::-;54379:583;;;54537:11;;-1:-1:-1;;;;;54537:11:0;:26;54564:23;54579:7;54564:14;:23::i;:::-;54537:51;;;;;;;;;;;;;160:25:1;;148:2;133:18;;14:177;54537:51:0;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;:::i;:::-;54528:60;;54379:583;;;54610:41;54643:7;54610:32;:41::i;:::-;54606:356;;;-1:-1:-1;;;;;54795:71:0;;54763:29;54795:71;;;:30;:71;;;;;:83;;;54902:48;54795:83;54902:25;:48::i;:::-;54893:57;54981:6;-1:-1:-1;;;;54234:761:0:o;24248:246::-;24349:4;-1:-1:-1;;;;;;24386:47:0;;-1:-1:-1;;;24386:47:0;;:100;;;24450:36;24474:11;24450:23;:36::i;25040:497::-;25121:22;25129:4;25135:7;25121;:22::i;:::-;25116:414;;25309:41;25337:7;-1:-1:-1;;;;;25309:41:0;25347:2;25309:19;:41::i;:::-;25423:38;25451:4;25458:2;25423:19;:38::i;:::-;25214:270;;;;;;;;;:::i;:::-;;;;-1:-1:-1;;25214:270:0;;;;;;;;;;-1:-1:-1;;;25160:358:0;;;;;;;:::i;28575:229::-;28650:22;28658:4;28664:7;28650;:22::i;:::-;28645:152;;28689:6;:12;;;;;;;;;;;-1:-1:-1;;;;;28689:29:0;;;;;;;;;:36;;-1:-1:-1;;28689:36:0;28721:4;28689:36;;;28772:12;683:10;;603:98;28772:12;-1:-1:-1;;;;;28745:40:0;28763:7;-1:-1:-1;;;;;28745:40:0;28757:4;28745:40;;;;;;;;;;28575:229;;:::o;42504:285::-;42702:68;;-1:-1:-1;;;;;22196:15:1;;;42702:68:0;;;22178:34:1;22248:15;;22228:18;;;22221:43;22280:18;;;22273:34;;;42648:133:0;;42682:5;;-1:-1:-1;;;42725:27:0;22113:18:1;;42702:68:0;;;;-1:-1:-1;;42702:68:0;;;;;;;;;;;;;;-1:-1:-1;;;;;42702:68:0;-1:-1:-1;;;;;;42702:68:0;;;;;;;;;;42648:19;:133::i;:::-;42504:285;;;;:::o;28812:230::-;28887:22;28895:4;28901:7;28887;:22::i;:::-;28883:152;;;28958:5;28926:12;;;;;;;;;;;-1:-1:-1;;;;;28926:29:0;;;;;;;;;;:37;;-1:-1:-1;;28926:37:0;;;28983:40;683:10;;28926:12;;28983:40;;28958:5;28983:40;28812:230;;:::o;42282:214::-;42365:123;42399:5;42442:23;;;42467:2;42471:5;42419:58;;;;;;;;;:::i;39198:265::-;39316:4;-1:-1:-1;;;;;;39353:49:0;;-1:-1:-1;;;39353:49:0;;:102;;-1:-1:-1;;;;;;;;;;9381:40:0;;;39419:36;9256:173;10963:476;11063:13;11089:19;11121:10;11125:6;11121:1;:10;:::i;:::-;:14;;11134:1;11121:14;:::i;:::-;11111:25;;;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;-1:-1:-1;11111:25:0;;11089:47;;-1:-1:-1;;;11147:6:0;11154:1;11147:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;11147:15:0;;;;;;;;;-1:-1:-1;;;11173:6:0;11180:1;11173:9;;;;;;;;:::i;:::-;;;;:15;-1:-1:-1;;;;;11173:15:0;;;;;;;;-1:-1:-1;11204:9:0;11216:10;11220:6;11216:1;:10;:::i;:::-;:14;;11229:1;11216:14;:::i;:::-;11204:26;;11199:135;11236:1;11232;:5;11199:135;;;-1:-1:-1;;;11284:5:0;11292:3;11284:11;11271:25;;;;;;;:::i;:::-;;;;11259:6;11266:1;11259:9;;;;;;;;:::i;:::-;;;;:37;-1:-1:-1;;;;;11259:37:0;;;;;;;;-1:-1:-1;11321:1:0;11311:11;;;;;11239:3;;;:::i;:::-;;;11199:135;;;-1:-1:-1;11352:10:0;;11344:55;;;;-1:-1:-1;;;11344:55:0;;22661:2:1;11344:55:0;;;22643:21:1;;;22680:18;;;22673:30;22739:34;22719:18;;;22712:62;22791:18;;11344:55:0;22459:356:1;44293:802:0;44717:23;44743:106;44785:4;44743:106;;;;;;;;;;;;;;;;;44751:5;-1:-1:-1;;;;;44743:27:0;;;:106;;;;;:::i;:::-;44864:17;;44717:132;;-1:-1:-1;44864:21:0;44860:228;;44979:10;44968:30;;;;;;;;;;;;:::i;:::-;44942:134;;;;-1:-1:-1;;;44942:134:0;;23304:2:1;44942:134:0;;;23286:21:1;23343:2;23323:18;;;23316:30;23382:34;23362:18;;;23355:62;-1:-1:-1;;;23433:18:1;;;23426:40;23483:19;;44942:134:0;23102:406:1;15032:229:0;15169:12;15201:52;15223:6;15231:4;15237:1;15240:12;15169;12450:20;;16572:60;;;;-1:-1:-1;;;16572:60:0;;24122:2:1;16572:60:0;;;24104:21:1;24161:2;24141:18;;;24134:30;24200:31;24180:18;;;24173:59;24249:18;;16572:60:0;23920:353:1;16572:60:0;16646:12;16660:23;16687:6;-1:-1:-1;;;;;16687:11:0;16706:5;16727:4;16687:55;;;;;;:::i;:::-;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;16645:97;;;;16760:51;16777:7;16786:10;16798:12;16760:16;:51::i;:::-;16753:58;16248:571;-1:-1:-1;;;;;;;16248:571:0:o;19203:712::-;19353:12;19382:7;19378:530;;;-1:-1:-1;19413:10:0;19406:17;;19378:530;19527:17;;:21;19523:374;;19725:10;19719:17;19786:15;19773:10;19769:2;19765:19;19758:44;19523:374;19868:12;19861:20;;-1:-1:-1;;;19861:20:0;;;;;;;;:::i;196:286:1:-;254:6;307:2;295:9;286:7;282:23;278:32;275:52;;;323:1;320;313:12;275:52;349:23;;-1:-1:-1;;;;;;401:32:1;;391:43;;381:71;;448:1;445;438:12;679:131;-1:-1:-1;;;;;754:31:1;;744:42;;734:70;;800:1;797;790:12;734:70;679:131;:::o;815:247::-;874:6;927:2;915:9;906:7;902:23;898:32;895:52;;;943:1;940;933:12;895:52;982:9;969:23;1001:31;1026:5;1001:31;:::i;1067:180::-;1126:6;1179:2;1167:9;1158:7;1154:23;1150:32;1147:52;;;1195:1;1192;1185:12;1147:52;-1:-1:-1;1218:23:1;;1067:180;-1:-1:-1;1067:180:1:o;1252:316::-;1329:6;1337;1345;1398:2;1386:9;1377:7;1373:23;1369:32;1366:52;;;1414:1;1411;1404:12;1366:52;-1:-1:-1;;1437:23:1;;;1507:2;1492:18;;1479:32;;-1:-1:-1;1558:2:1;1543:18;;;1530:32;;1252:316;-1:-1:-1;1252:316:1:o;1940:315::-;2008:6;2016;2069:2;2057:9;2048:7;2044:23;2040:32;2037:52;;;2085:1;2082;2075:12;2037:52;2121:9;2108:23;2098:33;;2181:2;2170:9;2166:18;2153:32;2194:31;2219:5;2194:31;:::i;:::-;2244:5;2234:15;;;1940:315;;;;;:::o;3674:949::-;3905:2;3957:21;;;4027:13;;3930:18;;;4049:22;;;3876:4;;3905:2;4090;;4108:18;;;;4149:15;;;3876:4;4192:405;4206:6;4203:1;4200:13;4192:405;;;4265:13;;4317:9;;4310:17;4303:25;4291:38;;4369:11;;;4363:18;4349:12;;;4342:40;4422:11;;;4416:18;4402:12;;;4395:40;4458:4;4502:11;;;4496:18;4482:12;;;4475:40;4544:4;4535:14;;;;4572:15;;;;4228:1;4221:9;4192:405;;;-1:-1:-1;4614:3:1;;3674:949;-1:-1:-1;;;;;;;3674:949:1:o;4907:127::-;4968:10;4963:3;4959:20;4956:1;4949:31;4999:4;4996:1;4989:15;5023:4;5020:1;5013:15;5039:275;5110:2;5104:9;5175:2;5156:13;;-1:-1:-1;;5152:27:1;5140:40;;5210:18;5195:34;;5231:22;;;5192:62;5189:88;;;5257:18;;:::i;:::-;5293:2;5286:22;5039:275;;-1:-1:-1;5039:275:1:o;5319:712::-;5373:5;5426:3;5419:4;5411:6;5407:17;5403:27;5393:55;;5444:1;5441;5434:12;5393:55;5480:6;5467:20;5506:4;5529:18;5525:2;5522:26;5519:52;;;5551:18;;:::i;:::-;5597:2;5594:1;5590:10;5620:28;5644:2;5640;5636:11;5620:28;:::i;:::-;5682:15;;;5752;;;5748:24;;;5713:12;;;;5784:15;;;5781:35;;;5812:1;5809;5802:12;5781:35;5848:2;5840:6;5836:15;5825:26;;5860:142;5876:6;5871:3;5868:15;5860:142;;;5942:17;;5930:30;;5893:12;;;;5980;;;;5860:142;;6036:530;6078:5;6131:3;6124:4;6116:6;6112:17;6108:27;6098:55;;6149:1;6146;6139:12;6098:55;6185:6;6172:20;6211:18;6207:2;6204:26;6201:52;;;6233:18;;:::i;:::-;6277:55;6320:2;6301:13;;-1:-1:-1;;6297:27:1;6326:4;6293:38;6277:55;:::i;:::-;6357:2;6348:7;6341:19;6403:3;6396:4;6391:2;6383:6;6379:15;6375:26;6372:35;6369:55;;;6420:1;6417;6410:12;6369:55;6485:2;6478:4;6470:6;6466:17;6459:4;6450:7;6446:18;6433:55;6533:1;6508:16;;;6526:4;6504:27;6497:38;;;;6512:7;6036:530;-1:-1:-1;;;6036:530:1:o;6571:1071::-;6725:6;6733;6741;6749;6757;6810:3;6798:9;6789:7;6785:23;6781:33;6778:53;;;6827:1;6824;6817:12;6778:53;6866:9;6853:23;6885:31;6910:5;6885:31;:::i;:::-;6935:5;-1:-1:-1;6992:2:1;6977:18;;6964:32;7005:33;6964:32;7005:33;:::i;:::-;7057:7;-1:-1:-1;7115:2:1;7100:18;;7087:32;7138:18;7168:14;;;7165:34;;;7195:1;7192;7185:12;7165:34;7218:61;7271:7;7262:6;7251:9;7247:22;7218:61;:::i;:::-;7208:71;;7332:2;7321:9;7317:18;7304:32;7288:48;;7361:2;7351:8;7348:16;7345:36;;;7377:1;7374;7367:12;7345:36;7400:63;7455:7;7444:8;7433:9;7429:24;7400:63;:::i;:::-;7390:73;;7516:3;7505:9;7501:19;7488:33;7472:49;;7546:2;7536:8;7533:16;7530:36;;;7562:1;7559;7552:12;7530:36;;7585:51;7628:7;7617:8;7606:9;7602:24;7585:51;:::i;:::-;7575:61;;;6571:1071;;;;;;;;:::o;8476:734::-;8580:6;8588;8596;8604;8612;8665:3;8653:9;8644:7;8640:23;8636:33;8633:53;;;8682:1;8679;8672:12;8633:53;8721:9;8708:23;8740:31;8765:5;8740:31;:::i;:::-;8790:5;-1:-1:-1;8847:2:1;8832:18;;8819:32;8860:33;8819:32;8860:33;:::i;:::-;8912:7;-1:-1:-1;8966:2:1;8951:18;;8938:32;;-1:-1:-1;9017:2:1;9002:18;;8989:32;;-1:-1:-1;9072:3:1;9057:19;;9044:33;9100:18;9089:30;;9086:50;;;9132:1;9129;9122:12;9086:50;9155:49;9196:7;9187:6;9176:9;9172:22;9155:49;:::i;9215:398::-;9417:2;9399:21;;;9456:2;9436:18;;;9429:30;9495:34;9490:2;9475:18;;9468:62;-1:-1:-1;;;9561:2:1;9546:18;;9539:32;9603:3;9588:19;;9215:398::o;9618:404::-;9820:2;9802:21;;;9859:2;9839:18;;;9832:30;9898:34;9893:2;9878:18;;9871:62;-1:-1:-1;;;9964:2:1;9949:18;;9942:38;10012:3;9997:19;;9618:404::o;10027:127::-;10088:10;10083:3;10079:20;10076:1;10069:31;10119:4;10116:1;10109:15;10143:4;10140:1;10133:15;10159:168;10232:9;;;10263;;10280:15;;;10274:22;;10260:37;10250:71;;10301:18;;:::i;10332:125::-;10397:9;;;10418:10;;;10415:36;;;10431:18;;:::i;10462:128::-;10529:9;;;10550:11;;;10547:37;;;10564:18;;:::i;10595:356::-;10797:2;10779:21;;;10816:18;;;10809:30;10875:34;10870:2;10855:18;;10848:62;10942:2;10927:18;;10595:356::o;10956:345::-;-1:-1:-1;;;;;11176:32:1;;;;11158:51;;11240:2;11225:18;;11218:34;;;;11283:2;11268:18;;11261:34;11146:2;11131:18;;10956:345::o;11695:127::-;11756:10;11751:3;11747:20;11744:1;11737:31;11787:4;11784:1;11777:15;11811:4;11808:1;11801:15;11827:135;11866:3;11887:17;;;11884:43;;11907:18;;:::i;:::-;-1:-1:-1;11954:1:1;11943:13;;11827:135::o;12389:404::-;12591:2;12573:21;;;12630:2;12610:18;;;12603:30;12669:34;12664:2;12649:18;;12642:62;-1:-1:-1;;;12735:2:1;12720:18;;12713:38;12783:3;12768:19;;12389:404::o;12798:::-;13000:2;12982:21;;;13039:2;13019:18;;;13012:30;13078:34;13073:2;13058:18;;13051:62;-1:-1:-1;;;13144:2:1;13129:18;;13122:38;13192:3;13177:19;;12798:404::o;13415:184::-;13485:6;13538:2;13526:9;13517:7;13513:23;13509:32;13506:52;;;13554:1;13551;13544:12;13506:52;-1:-1:-1;13577:16:1;;13415:184;-1:-1:-1;13415:184:1:o;13604:401::-;13806:2;13788:21;;;13845:2;13825:18;;;13818:30;13884:34;13879:2;13864:18;;13857:62;-1:-1:-1;;;13950:2:1;13935:18;;13928:35;13995:3;13980:19;;13604:401::o;14010:352::-;14212:2;14194:21;;;14251:2;14231:18;;;14224:30;14290;14285:2;14270:18;;14263:58;14353:2;14338:18;;14010:352::o;14728:274::-;-1:-1:-1;;;;;14920:32:1;;;;14902:51;;14984:2;14969:18;;14962:34;14890:2;14875:18;;14728:274::o;16494:217::-;16534:1;16560;16550:132;;16604:10;16599:3;16595:20;16592:1;16585:31;16639:4;16636:1;16629:15;16667:4;16664:1;16657:15;16550:132;-1:-1:-1;16696:9:1;;16494:217::o;17068:635::-;-1:-1:-1;;;;;17427:15:1;;;17409:34;;17479:15;;;;17474:2;17459:18;;17452:43;17526:2;17511:18;;17504:34;17569:2;17554:18;;17547:34;;;;17389:3;17612;17597:19;;17590:32;;;17352:4;17638:19;;;17631:30;17693:3;17678:19;;17068:635::o;18886:351::-;19088:2;19070:21;;;19127:2;19107:18;;;19100:30;19166:29;19161:2;19146:18;;19139:57;19228:2;19213:18;;18886:351::o;20465:250::-;20550:1;20560:113;20574:6;20571:1;20568:13;20560:113;;;20650:11;;;20644:18;20631:11;;;20624:39;20596:2;20589:10;20560:113;;;-1:-1:-1;;20707:1:1;20689:16;;20682:27;20465:250::o;20720:812::-;21131:25;21126:3;21119:38;21101:3;21186:6;21180:13;21202:75;21270:6;21265:2;21260:3;21256:12;21249:4;21241:6;21237:17;21202:75;:::i;:::-;-1:-1:-1;;;21336:2:1;21296:16;;;21328:11;;;21321:40;21386:13;;21408:76;21386:13;21470:2;21462:11;;21455:4;21443:17;;21408:76;:::i;:::-;21504:17;21523:2;21500:26;;20720:812;-1:-1:-1;;;;20720:812:1:o;21537:396::-;21686:2;21675:9;21668:21;21649:4;21718:6;21712:13;21761:6;21756:2;21745:9;21741:18;21734:34;21777:79;21849:6;21844:2;21833:9;21829:18;21824:2;21816:6;21812:15;21777:79;:::i;:::-;21917:2;21896:15;-1:-1:-1;;21892:29:1;21877:45;;;;21924:2;21873:54;;21537:396;-1:-1:-1;;21537:396:1:o;22318:136::-;22357:3;22385:5;22375:39;;22394:18;;:::i;:::-;-1:-1:-1;;;22430:18:1;;22318:136::o;22820:277::-;22887:6;22940:2;22928:9;22919:7;22915:23;22911:32;22908:52;;;22956:1;22953;22946:12;22908:52;22988:9;22982:16;23041:5;23034:13;23027:21;23020:5;23017:32;23007:60;;23063:1;23060;23053:12;24278:287;24407:3;24445:6;24439:13;24461:66;24520:6;24515:3;24508:4;24500:6;24496:17;24461:66;:::i;:::-;24543:16;;;;;24278:287;-1:-1:-1;;24278:287:1:o
Swarm Source
ipfs://67d4062d6fc8607b22438ab1050c07400873052d52dc01ccb20934a8a5b1e695
Loading...
Loading
Loading...
Loading
Loading...
Loading
Net Worth in USD
$337.12
Net Worth in S
Token Allocations
FS
100.00%
Multichain Portfolio | 35 Chains
| Chain | Token | Portfolio % | Price | Amount | Value |
|---|---|---|---|---|---|
| SONIC | 100.00% | $0.000023 | 14,942,000 | $337.12 |
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.