More Info
Private Name Tags
ContractCreator
Latest 25 from a total of 386 transactions
Transaction Hash |
Method
|
Block
|
From
|
To
|
|||||
---|---|---|---|---|---|---|---|---|---|
Redeem | 20644286 | 157 days ago | IN | 0 ETH | 0.00009331 | ||||
Redeem | 20643897 | 157 days ago | IN | 0 ETH | 0.00005991 | ||||
Redeem | 20594603 | 164 days ago | IN | 0 ETH | 0.00009723 | ||||
Redeem | 20586295 | 165 days ago | IN | 0 ETH | 0.00008389 | ||||
Redeem | 20521056 | 174 days ago | IN | 0 ETH | 0.00051415 | ||||
Redeem | 20514689 | 175 days ago | IN | 0 ETH | 0.00024821 | ||||
Redeem | 20487766 | 179 days ago | IN | 0 ETH | 0.00014042 | ||||
Redeem | 20412466 | 189 days ago | IN | 0 ETH | 0.00018641 | ||||
Redeem | 20412460 | 189 days ago | IN | 0 ETH | 0.0002518 | ||||
Redeem | 20031411 | 243 days ago | IN | 0 ETH | 0.00121142 | ||||
Redeem | 20000785 | 247 days ago | IN | 0 ETH | 0.00020183 | ||||
Redeem | 19978191 | 250 days ago | IN | 0 ETH | 0.00036071 | ||||
Redeem | 19978149 | 250 days ago | IN | 0 ETH | 0.00028573 | ||||
Redeem | 19978145 | 250 days ago | IN | 0 ETH | 0.00054159 | ||||
Redeem | 19978141 | 250 days ago | IN | 0 ETH | 0.00055136 | ||||
Redeem | 19932580 | 256 days ago | IN | 0 ETH | 0.00121011 | ||||
Redeem | 19912576 | 259 days ago | IN | 0 ETH | 0.00106677 | ||||
Redeem | 19886694 | 263 days ago | IN | 0 ETH | 0.00018534 | ||||
Redeem | 19886693 | 263 days ago | IN | 0 ETH | 0.00025524 | ||||
Redeem | 19800428 | 275 days ago | IN | 0 ETH | 0.0002349 | ||||
Redeem | 19800392 | 275 days ago | IN | 0 ETH | 0.00028896 | ||||
Redeem | 19782784 | 277 days ago | IN | 0 ETH | 0.00068565 | ||||
Redeem | 19768799 | 279 days ago | IN | 0 ETH | 0.00134229 | ||||
Redeem | 19748752 | 282 days ago | IN | 0 ETH | 0.00037116 | ||||
Redeem | 19727981 | 285 days ago | IN | 0 ETH | 0.0004738 |
View more zero value Internal Transactions in Advanced View mode
Advanced mode:
Loading...
Loading
Contract Source Code Verified (Exact Match)
Contract Name:
WhitelistTheopetraBondDepository
Compiler Version
v0.8.10+commit.fc410830
Contract Source Code (Solidity Standard Json-Input format)
// SPDX-License-Identifier: AGPL-3.0 pragma solidity ^0.8.10; import "../Types/NoteKeeper.sol"; import "../Types/Signed.sol"; import "../Types/PriceConsumerV3.sol"; import "../Libraries/SafeERC20.sol"; import "../Interfaces/IERC20Metadata.sol"; import "../Interfaces/IWhitelistBondDepository.sol"; /** * @title Theopetra Whitelist Bond Depository */ contract WhitelistTheopetraBondDepository is IWhitelistBondDepository, NoteKeeper, Signed, PriceConsumerV3 { /* ======== DEPENDENCIES ======== */ using SafeERC20 for IERC20; /* ======== EVENTS ======== */ event CreateMarket( uint256 indexed id, address indexed baseToken, address indexed quoteToken, uint256 fixedBondPrice ); event CloseMarket(uint256 indexed id); event Bond(uint256 indexed id, uint256 amount, uint256 price); /* ======== STATE VARIABLES ======== */ // Storage Market[] public markets; // persistent market data Terms[] public terms; // deposit construction data Metadata[] public metadata; // extraneous market data address private wethHelper; // Queries mapping(address => uint256[]) public marketsForQuote; // market IDs for quote token /* ======== CONSTRUCTOR ======== */ constructor( ITheopetraAuthority _authority, IERC20 _theo, IStakedTHEOToken _stheo, IStaking _staking, ITreasury _treasury ) NoteKeeper(_authority, _theo, _stheo, _staking, _treasury) { // save gas for users by bulk approving stake() transactions _theo.approve(address(_staking), 1e45); } /* ======== DEPOSIT ======== */ /** * @notice deposit quote tokens in exchange for a bond from a specified market * @param _id the ID of the market * @param _amount the amount of quote token to spend * @param _maxPrice the maximum price at which to buy * @param _user the recipient of the payout * @param _referral the front end operator address * @return depositInfo DepositInfo */ function deposit( uint256 _id, uint256 _amount, uint256 _maxPrice, address _user, address _referral, bytes calldata signature ) external override returns (DepositInfo memory depositInfo) { if (msg.sender != wethHelper) { verifySignature("", signature); } Market storage market = markets[_id]; Terms memory term = terms[_id]; uint48 currentTime = uint48(block.timestamp); // Markets end at a defined timestamp // |-------------------------------------| t require(currentTime < term.conclusion, "Depository: market concluded"); // Get the price of THEO in quote token terms // i.e. the number of quote tokens per THEO // With 9 decimal places uint256 price = calculatePrice(_id); // Users input a maximum price, which protects them from price changes after // entering the mempool. max price is a slippage mitigation measure require(price <= _maxPrice, "Depository: more than max price"); /** * payout for the deposit = amount / price * * where * payout = THEO out, in THEO decimals (9) * amount = quote tokens in * price = quote tokens per THEO, in THEO decimals (9) * * 1e18 = THEO decimals (9) + price decimals (9) */ depositInfo.payout_ = ((_amount * 1e18) / price) / (10**metadata[_id].quoteDecimals); /* * each market is initialized with a capacity * * this is either the number of THEO that the market can sell * (if capacity in quote is false), * * or the number of quote tokens that the market can buy * (if capacity in quote is true) */ require( market.capacity >= (market.capacityInQuote ? _amount : depositInfo.payout_), "Depository: capacity exceeded" ); market.capacity -= market.capacityInQuote ? _amount : depositInfo.payout_; if (market.capacity == 0) { emit CloseMarket(_id); } /** * bonds mature with a cliff at a set timestamp * prior to the expiry timestamp, no payout tokens are accessible to the user * after the expiry timestamp, the entire payout can be redeemed * * there are two types of bonds: fixed-term and fixed-expiration * * fixed-term bonds mature in a set amount of time from deposit * i.e. term = 1 week. when alice deposits on day 1, her bond * expires on day 8. when bob deposits on day 2, his bond expires day 9. * * fixed-expiration bonds mature at a set timestamp * i.e. expiration = day 10. when alice deposits on day 1, her term * is 9 days. when bob deposits on day 2, his term is 8 days. */ depositInfo.expiry_ = term.fixedTerm ? term.vesting + currentTime : term.vesting; // markets keep track of how many quote tokens have been // purchased, and how much THEO has been sold market.purchased += _amount; market.sold += uint64(depositInfo.payout_); emit Bond(_id, _amount, price); /** * user data is stored as Notes. these are isolated array entries * storing the amount due, the time created, the time when payout * is redeemable, the time when payout was redeemed, and the ID * of the market deposited into */ depositInfo.index_ = addNote( _user, depositInfo.payout_, uint48(depositInfo.expiry_), uint48(_id), _referral, 0, false ); // transfer payment to treasury market.quoteToken.safeTransferFrom(msg.sender, address(treasury), _amount); } /* ======== CREATE ======== */ /** * @notice creates a new market type * @dev current price should be in 9 decimals. * @param _quoteToken token used to deposit * @param _market [capacity (in THEO or quote), fixed bond price (9 decimals) USD per THEO] * @param _booleans [capacity in quote, fixed term] * @param _terms [vesting length (if fixed term) or vested timestamp, conclusion timestamp] * @param _priceFeed address of the price consumer, to return the USD value for the quote token when deposits are made * @return id_ ID of new bond market */ function create( IERC20 _quoteToken, address _priceFeed, uint256[2] memory _market, bool[2] memory _booleans, uint256[2] memory _terms ) external override onlyPolicy returns (uint256 id_) { // the decimal count of the quote token uint256 decimals = IERC20Metadata(address(_quoteToken)).decimals(); // depositing into, or getting info for, the created market uses this ID id_ = markets.length; markets.push( Market({ quoteToken: _quoteToken, priceFeed: _priceFeed, capacityInQuote: _booleans[0], capacity: _market[0], purchased: 0, sold: 0, usdPricePerTHEO: _market[1] }) ); terms.push(Terms({ fixedTerm: _booleans[1], vesting: uint48(_terms[0]), conclusion: uint48(_terms[1]) })); metadata.push(Metadata({ quoteDecimals: uint8(decimals) })); marketsForQuote[address(_quoteToken)].push(id_); emit CreateMarket(id_, address(theo), address(_quoteToken), _market[1]); } /** * @notice disable existing market * @param _id ID of market to close */ function close(uint256 _id) external override onlyPolicy { terms[_id].conclusion = uint48(block.timestamp); markets[_id].capacity = 0; emit CloseMarket(_id); } /* ======== EXTERNAL VIEW ======== */ /** * @notice payout due for amount of quote tokens * @param _amount amount of quote tokens to spend * @param _id ID of market * @return amount of THEO to be paid in THEO decimals * * @dev 1e18 = theo decimals (9) + fixed bond price decimals (9) */ function payoutFor(uint256 _amount, uint256 _id) external view override returns (uint256) { Metadata memory meta = metadata[_id]; return (_amount * 1e18) / calculatePrice(_id) / 10**meta.quoteDecimals; } /** * @notice is a given market accepting deposits * @param _id ID of market */ function isLive(uint256 _id) public view override returns (bool) { return (markets[_id].capacity != 0 && terms[_id].conclusion > block.timestamp); } /** * @notice returns an array of all active market IDs */ function liveMarkets() external view override returns (uint256[] memory) { uint256 num; for (uint256 i = 0; i < markets.length; i++) { if (isLive(i)) num++; } uint256[] memory ids = new uint256[](num); uint256 nonce; for (uint256 i = 0; i < markets.length; i++) { if (isLive(i)) { ids[nonce] = i; nonce++; } } return ids; } /** * @notice returns an array of all active market IDs for a given quote token * @param _token quote token to check for */ function liveMarketsFor(address _token) external view override returns (uint256[] memory) { uint256[] memory mkts = marketsForQuote[_token]; uint256 num; for (uint256 i = 0; i < mkts.length; i++) { if (isLive(mkts[i])) num++; } uint256[] memory ids = new uint256[](num); uint256 nonce; for (uint256 i = 0; i < mkts.length; i++) { if (isLive(mkts[i])) { ids[nonce] = mkts[i]; nonce++; } } return ids; } /** * @notice returns an array of market IDs for historical analysis */ function getMarkets() external view override returns (uint256[] memory) { uint256[] memory ids = new uint256[](markets.length); for (uint256 i = 0; i < markets.length; i++) { ids[i] = i; } return ids; } /** * @notice returns an array of all market IDs for a given quote token * @param _token quote token to check for */ function getMarketsFor(address _token) external view override returns (uint256[] memory) { uint256[] memory mkts = marketsForQuote[_token]; uint256[] memory ids = new uint256[](mkts.length); for (uint256 i = 0; i < mkts.length; i++) { ids[i] = mkts[i]; } return ids; } /** * @notice calculate the price of THEO in quote token terms; i.e. the number of quote tokens per THEO * @dev get the latest price for the market's quote token in USD * (`priceConsumerPrice`, with decimals `priceConsumerDecimals`) * then `scalePrice` to scale the fixed bond price to THEO decimals when calculating `price`. * finally, calculate `price` as quote tokens per THEO, in THEO decimals (9) * @param _id market ID * @return uint256 price of THEO in quote token terms, in THEO decimals (9) */ function calculatePrice(uint256 _id) public view override returns (uint256) { (int256 priceConsumerPrice, uint8 priceConsumerDecimals) = getLatestPrice(markets[_id].priceFeed); int256 scaledPrice = scalePrice(int256(markets[_id].usdPricePerTHEO), 9, 9 + priceConsumerDecimals); uint256 price = uint256(scaledPrice / priceConsumerPrice); return price; } /* ======== INTERNAL PURE ======== */ /** * @param _price fixed bond price (USD per THEO), 9 decimals * @param _priceDecimals decimals (9) used for the fixed bond price * @param _decimals sum of decimals for THEO token (9) + decimals for the price feed */ function scalePrice( int256 _price, uint8 _priceDecimals, uint8 _decimals ) internal pure returns (int256) { if (_priceDecimals < _decimals) { return _price * int256(10**uint256(_decimals - _priceDecimals)); } else if (_priceDecimals > _decimals) { return _price / int256(10**uint256(_priceDecimals - _decimals)); } return _price; } /* ====== POLICY FUNCTIONS ====== */ function setWethHelper(address _wethHelper) external onlyGovernor { require(_wethHelper != address(0), "Zero address"); wethHelper = _wethHelper; } }
// SPDX-License-Identifier: MIT pragma solidity ^0.8.0; interface AggregatorV3Interface { function decimals() external view returns (uint8); function description() external view returns (string memory); function version() external view returns (uint256); // getRoundData and latestRoundData should both raise "No data present" // if they do not have data to report, instead of returning unset values // which could be misinterpreted as actual reported values. function getRoundData(uint80 _roundId) external view returns ( uint80 roundId, int256 answer, uint256 startedAt, uint256 updatedAt, uint80 answeredInRound ); function latestRoundData() external view returns ( uint80 roundId, int256 answer, uint256 startedAt, uint256 updatedAt, uint80 answeredInRound ); }
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts v4.4.1 (utils/Strings.sol) pragma solidity ^0.8.0; /** * @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); } }
// SPDX-License-Identifier: MIT // OpenZeppelin Contracts (last updated v4.5.0) (utils/cryptography/ECDSA.sol) pragma solidity ^0.8.0; import "../Strings.sol"; /** * @dev Elliptic Curve Digital Signature Algorithm (ECDSA) operations. * * These functions can be used to verify that a message was signed by the holder * of the private keys of a given address. */ library ECDSA { enum RecoverError { NoError, InvalidSignature, InvalidSignatureLength, InvalidSignatureS, InvalidSignatureV } function _throwError(RecoverError error) private pure { if (error == RecoverError.NoError) { return; // no error: do nothing } else if (error == RecoverError.InvalidSignature) { revert("ECDSA: invalid signature"); } else if (error == RecoverError.InvalidSignatureLength) { revert("ECDSA: invalid signature length"); } else if (error == RecoverError.InvalidSignatureS) { revert("ECDSA: invalid signature 's' value"); } else if (error == RecoverError.InvalidSignatureV) { revert("ECDSA: invalid signature 'v' value"); } } /** * @dev Returns the address that signed a hashed message (`hash`) with * `signature` or error string. This address can then be used for verification purposes. * * The `ecrecover` EVM opcode allows for malleable (non-unique) signatures: * this function rejects them by requiring the `s` value to be in the lower * half order, and the `v` value to be either 27 or 28. * * IMPORTANT: `hash` _must_ be the result of a hash operation for the * verification to be secure: it is possible to craft signatures that * recover to arbitrary addresses for non-hashed data. A safe way to ensure * this is by receiving a hash of the original message (which may otherwise * be too long), and then calling {toEthSignedMessageHash} on it. * * Documentation for signature generation: * - with https://web3js.readthedocs.io/en/v1.3.4/web3-eth-accounts.html#sign[Web3.js] * - with https://docs.ethers.io/v5/api/signer/#Signer-signMessage[ethers] * * _Available since v4.3._ */ function tryRecover(bytes32 hash, bytes memory signature) internal pure returns (address, RecoverError) { // Check the signature length // - case 65: r,s,v signature (standard) // - case 64: r,vs signature (cf https://eips.ethereum.org/EIPS/eip-2098) _Available since v4.1._ if (signature.length == 65) { bytes32 r; bytes32 s; uint8 v; // ecrecover takes the signature parameters, and the only way to get them // currently is to use assembly. assembly { r := mload(add(signature, 0x20)) s := mload(add(signature, 0x40)) v := byte(0, mload(add(signature, 0x60))) } return tryRecover(hash, v, r, s); } else if (signature.length == 64) { bytes32 r; bytes32 vs; // ecrecover takes the signature parameters, and the only way to get them // currently is to use assembly. assembly { r := mload(add(signature, 0x20)) vs := mload(add(signature, 0x40)) } return tryRecover(hash, r, vs); } else { return (address(0), RecoverError.InvalidSignatureLength); } } /** * @dev Returns the address that signed a hashed message (`hash`) with * `signature`. This address can then be used for verification purposes. * * The `ecrecover` EVM opcode allows for malleable (non-unique) signatures: * this function rejects them by requiring the `s` value to be in the lower * half order, and the `v` value to be either 27 or 28. * * IMPORTANT: `hash` _must_ be the result of a hash operation for the * verification to be secure: it is possible to craft signatures that * recover to arbitrary addresses for non-hashed data. A safe way to ensure * this is by receiving a hash of the original message (which may otherwise * be too long), and then calling {toEthSignedMessageHash} on it. */ function recover(bytes32 hash, bytes memory signature) internal pure returns (address) { (address recovered, RecoverError error) = tryRecover(hash, signature); _throwError(error); return recovered; } /** * @dev Overload of {ECDSA-tryRecover} that receives the `r` and `vs` short-signature fields separately. * * See https://eips.ethereum.org/EIPS/eip-2098[EIP-2098 short signatures] * * _Available since v4.3._ */ function tryRecover( bytes32 hash, bytes32 r, bytes32 vs ) internal pure returns (address, RecoverError) { bytes32 s = vs & bytes32(0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff); uint8 v = uint8((uint256(vs) >> 255) + 27); return tryRecover(hash, v, r, s); } /** * @dev Overload of {ECDSA-recover} that receives the `r and `vs` short-signature fields separately. * * _Available since v4.2._ */ function recover( bytes32 hash, bytes32 r, bytes32 vs ) internal pure returns (address) { (address recovered, RecoverError error) = tryRecover(hash, r, vs); _throwError(error); return recovered; } /** * @dev Overload of {ECDSA-tryRecover} that receives the `v`, * `r` and `s` signature fields separately. * * _Available since v4.3._ */ function tryRecover( bytes32 hash, uint8 v, bytes32 r, bytes32 s ) internal pure returns (address, RecoverError) { // EIP-2 still allows signature malleability for ecrecover(). Remove this possibility and make the signature // unique. Appendix F in the Ethereum Yellow paper (https://ethereum.github.io/yellowpaper/paper.pdf), defines // the valid range for s in (301): 0 < s < secp256k1n ÷ 2 + 1, and for v in (302): v ∈ {27, 28}. Most // signatures from current libraries generate a unique signature with an s-value in the lower half order. // // If your library generates malleable signatures, such as s-values in the upper range, calculate a new s-value // with 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - s1 and flip v from 27 to 28 or // vice versa. If your library also generates signatures with 0/1 for v instead 27/28, add 27 to v to accept // these malleable signatures as well. if (uint256(s) > 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0) { return (address(0), RecoverError.InvalidSignatureS); } if (v != 27 && v != 28) { return (address(0), RecoverError.InvalidSignatureV); } // If the signature is valid (and not malleable), return the signer address address signer = ecrecover(hash, v, r, s); if (signer == address(0)) { return (address(0), RecoverError.InvalidSignature); } return (signer, RecoverError.NoError); } /** * @dev Overload of {ECDSA-recover} that receives the `v`, * `r` and `s` signature fields separately. */ function recover( bytes32 hash, uint8 v, bytes32 r, bytes32 s ) internal pure returns (address) { (address recovered, RecoverError error) = tryRecover(hash, v, r, s); _throwError(error); return recovered; } /** * @dev Returns an Ethereum Signed Message, created from a `hash`. This * produces hash corresponding to the one signed with the * https://eth.wiki/json-rpc/API#eth_sign[`eth_sign`] * JSON-RPC method as part of EIP-191. * * See {recover}. */ function toEthSignedMessageHash(bytes32 hash) internal pure returns (bytes32) { // 32 is the length in bytes of hash, // enforced by the type signature above return keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", hash)); } /** * @dev Returns an Ethereum Signed Message, created from `s`. This * produces hash corresponding to the one signed with the * https://eth.wiki/json-rpc/API#eth_sign[`eth_sign`] * JSON-RPC method as part of EIP-191. * * See {recover}. */ function toEthSignedMessageHash(bytes memory s) internal pure returns (bytes32) { return keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n", Strings.toString(s.length), s)); } /** * @dev Returns an Ethereum Signed Typed Data, created from a * `domainSeparator` and a `structHash`. This produces hash corresponding * to the one signed with the * https://eips.ethereum.org/EIPS/eip-712[`eth_signTypedData`] * JSON-RPC method as part of EIP-712. * * See {recover}. */ function toTypedDataHash(bytes32 domainSeparator, bytes32 structHash) internal pure returns (bytes32) { return keccak256(abi.encodePacked("\x19\x01", domainSeparator, structHash)); } }
// SPDX-License-Identifier: AGPL-1.0 pragma solidity >=0.7.5 <=0.8.10; interface IBondCalculator { function valuation(address tokenIn, uint256 amount_) external view returns (uint256 amountOut); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; interface IERC20 { function totalSupply() external view returns (uint256); function balanceOf(address account) external view returns (uint256); function transfer(address recipient, uint256 amount) external returns (bool); function allowance(address owner, address spender) external view returns (uint256); function approve(address spender, uint256 amount) external returns (bool); function transferFrom( address sender, address recipient, uint256 amount ) external returns (bool); event Transfer(address indexed from, address indexed to, uint256 value); event Approval(address indexed owner, address indexed spender, uint256 value); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; import "./IERC20.sol"; interface IERC20Metadata is IERC20 { function name() external view returns (string memory); function symbol() external view returns (string memory); function decimals() external view returns (uint8); }
// SPDX-License-Identifier: AGPL-3.0-only pragma solidity >=0.7.5; interface INoteKeeper { /** * @notice Info for market note * @dev Note::payout is sTHEO remaining to be paid * Note::created is the time the Note was created * Note::matured is the timestamp when the Note is redeemable * Note::redeemed is time market was redeemed * Note::marketID is market ID of deposit. uint48 to avoid adding a slot. */ struct Note { uint256 payout; uint48 created; uint48 matured; uint48 redeemed; uint48 marketID; uint48 discount; bool autoStake; } function redeem(address _user, uint256[] memory _indexes) external returns (uint256); function redeemAll(address _user) external returns (uint256); function pushNote(address to, uint256 index) external; function pullNote(address from, uint256 index) external returns (uint256 newIndex_); function indexesFor(address _user) external view returns (uint256[] memory); function pendingFor(address _user, uint256 _index) external view returns ( uint256 payout_, uint48 created_, uint48 expiry_, uint48 timeRemaining_, bool matured_, uint48 discount_ ); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; import "./IERC20.sol"; interface IStakedTHEOToken is IERC20 { function rebase(uint256 theoProfit_, uint256 epoch_) external returns (uint256); function circulatingSupply() external view returns (uint256); function balanceOf(address who) external view override returns (uint256); function gonsForBalance(uint256 amount) external view returns (uint256); function balanceForGons(uint256 gons) external view returns (uint256); function index() external view returns (uint256); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; interface IStaking { function stake( address _to, uint256 _amount, bool _claim ) external returns (uint256, uint256 _index); function claim(address _recipient, bool _rebasing) external returns (uint256); function forfeit(uint256 _index) external; function toggleLock() external; function unstake( address _to, uint256 _amount, bool _trigger, bool _rebasing ) external returns (uint256); function wrap(address _to, uint256 _amount) external returns (uint256 gBalance_); function unwrap(address _to, uint256 _amount) external returns (uint256 sBalance_); function rebase() external; function index() external view returns (uint256); function contractBalance() external view returns (uint256); function totalStaked() external view returns (uint256); function supplyInWarmup() external view returns (uint256); function indexesFor(address _user) external view returns (uint256[] memory); function claimAll(address _recipient) external returns (uint256); function pushClaim(address _to, uint256 _index) external; function pullClaim(address _from, uint256 _index) external returns (uint256 newIndex_); function pushClaimForBond(address _to, uint256 _index) external returns (uint256 newIndex_); function basis() external view returns (address); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; interface ITheopetraAuthority { /* ========== EVENTS ========== */ event GovernorPushed(address indexed from, address indexed to, bool _effectiveImmediately); event GuardianPushed(address indexed from, address indexed to, bool _effectiveImmediately); event PolicyPushed(address indexed from, address indexed to, bool _effectiveImmediately); event ManagerPushed(address indexed from, address indexed to, bool _effectiveImmediately); event VaultPushed(address indexed from, address indexed to, bool _effectiveImmediately); event SignerPushed(address indexed from, address indexed to, bool _effectiveImmediately); event GovernorPulled(address indexed from, address indexed to); event GuardianPulled(address indexed from, address indexed to); event PolicyPulled(address indexed from, address indexed to); event ManagerPulled(address indexed from, address indexed to); event VaultPulled(address indexed from, address indexed to); event SignerPulled(address indexed from, address indexed to); /* ========== VIEW ========== */ function governor() external view returns (address); function guardian() external view returns (address); function policy() external view returns (address); function manager() external view returns (address); function vault() external view returns (address); function whitelistSigner() external view returns (address); }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; import "./IBondCalculator.sol"; interface ITreasury { function deposit( uint256 _amount, address _token, uint256 _profit ) external returns (uint256); function withdraw(uint256 _amount, address _token) external; function tokenValue(address _token, uint256 _amount) external view returns (uint256 value_); function mint(address _recipient, uint256 _amount) external; function manage(address _token, uint256 _amount) external; function incurDebt(uint256 amount_, address token_) external; function repayDebtWithReserve(uint256 amount_, address token_) external; function tokenPerformanceUpdate() external; function baseSupply() external view returns (uint256); function deltaTokenPrice() external view returns (int256); function deltaTreasuryYield() external view returns (int256); function getTheoBondingCalculator() external view returns (IBondCalculator); function setTheoBondingCalculator(address _theoBondingCalculator) external; }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity >=0.7.5; import "./IERC20.sol"; interface IWhitelistBondDepository { /** * @notice Info about each type of market * @dev Market::capacity is capacity remaining * Market::quoteToken is token to accept as payment * Market::priceFeed is address of the price consumer, to return the USD value for the quote token when deposits are made * Market::capacityInQuote is in payment token (true) or in THEO (false, default) * Market::sold is base tokens out * Market::purchased quote tokens in * Market::usdPricePerTHEO is 9 decimal USD value for each THEO bond */ struct Market { uint256 capacity; IERC20 quoteToken; address priceFeed; bool capacityInQuote; uint64 sold; uint256 purchased; uint256 usdPricePerTHEO; } /** * @notice Info for creating new markets * @dev Terms::fixedTerm is fixed term or fixed expiration * Terms::vesting is length of time from deposit to maturity if fixed-term * Terms::conclusion is timestamp when market no longer offered (doubles as time when market matures if fixed-expiry) */ struct Terms { bool fixedTerm; uint48 vesting; uint48 conclusion; } /** * @notice Additional info about market * @dev Metadata::quoteDecimals is decimals of quote token */ struct Metadata { uint8 quoteDecimals; } struct DepositInfo { uint256 payout_; uint256 expiry_; uint256 index_; } /** * @notice deposit market * @param _bid uint256 * @param _amount uint256 * @param _maxPrice uint256 * @param _user address * @param _referral address * @param signature bytes * @return depositInfo DepositInfo */ function deposit( uint256 _bid, uint256 _amount, uint256 _maxPrice, address _user, address _referral, bytes calldata signature ) external returns (DepositInfo memory depositInfo); /** * @notice create market * @param _quoteToken IERC20 is the token used to deposit * @param _priceFeed address is address of the price consumer, to return the USD value for the quote token when deposits are made * @param _market uint256[2] is [capacity, fixed bond price (9 decimals) USD per THEO] * @param _booleans bool[2] is [capacity in quote, fixed term] * @param _terms uint256[2] is [vesting, conclusion] * @return id_ uint256 is ID of the market */ function create( IERC20 _quoteToken, address _priceFeed, uint256[2] memory _market, bool[2] memory _booleans, uint256[2] memory _terms ) external returns (uint256 id_); function close(uint256 _id) external; function isLive(uint256 _bid) external view returns (bool); function liveMarkets() external view returns (uint256[] memory); function liveMarketsFor(address _quoteToken) external view returns (uint256[] memory); function getMarkets() external view returns (uint256[] memory); function getMarketsFor(address _quoteToken) external view returns (uint256[] memory); function calculatePrice(uint256 _bid) external view returns (uint256); function payoutFor(uint256 _amount, uint256 _bid) external view returns (uint256); }
// SPDX-License-Identifier: AGPL-3.0-only pragma solidity >=0.7.5; import { IERC20 } from "../Interfaces/IERC20.sol"; /// @notice Safe IERC20 and ETH transfer library that safely handles missing return values. /// @author Modified from Uniswap (https://github.com/Uniswap/uniswap-v3-periphery/blob/main/contracts/libraries/TransferHelper.sol) /// Taken from Solmate library SafeERC20 { function safeTransferFrom( IERC20 token, address from, address to, uint256 amount ) internal { (bool success, bytes memory data) = address(token).call( abi.encodeWithSelector(IERC20.transferFrom.selector, from, to, amount) ); require(success && (data.length == 0 || abi.decode(data, (bool))), "TRANSFER_FROM_FAILED"); } function safeTransfer( IERC20 token, address to, uint256 amount ) internal { (bool success, bytes memory data) = address(token).call( abi.encodeWithSelector(IERC20.transfer.selector, to, amount) ); require(success && (data.length == 0 || abi.decode(data, (bool))), "TRANSFER_FAILED"); } function safeApprove( IERC20 token, address to, uint256 amount ) internal { (bool success, bytes memory data) = address(token).call( abi.encodeWithSelector(IERC20.approve.selector, to, amount) ); require(success && (data.length == 0 || abi.decode(data, (bool))), "APPROVE_FAILED"); } function safeTransferETH(address to, uint256 amount) internal { (bool success, ) = to.call{ value: amount }(new bytes(0)); require(success, "ETH_TRANSFER_FAILED"); } }
// SPDX-License-Identifier: AGPL-3.0-only pragma solidity ^0.8.10; import "../Types/TheopetraAccessControlled.sol"; import "../Interfaces/IERC20.sol"; abstract contract FrontEndRewarder is TheopetraAccessControlled { /* ========= STATE VARIABLES ========== */ uint256 public daoReward; // % reward for dao (3 decimals: 100 = 1%) uint256 public refReward; // % reward for referrer (3 decimals: 100 = 1%) mapping(address => uint256) public rewards; // front end operator rewards mapping(address => bool) public whitelisted; // whitelisted status for operators IERC20 internal immutable theo; // reward token event SetRewards(uint256 toRef, uint256 toDao); constructor(ITheopetraAuthority _authority, IERC20 _theo) TheopetraAccessControlled(_authority) { theo = _theo; } /* ========= EXTERNAL FUNCTIONS ========== */ // pay reward to front end operator function getReward() external { uint256 reward = rewards[msg.sender]; rewards[msg.sender] = 0; theo.transfer(msg.sender, reward); } /* ========= INTERNAL ========== */ /** * @notice add new market payout to user data */ function _giveRewards(uint256 _payout, address _referral) internal returns (uint256) { // first we calculate rewards paid to the DAO and to the front end operator (referrer) uint256 toDAO = (_payout * daoReward) / 1e4; uint256 toRef = (_payout * refReward) / 1e4; // and store them in our rewards mapping if (whitelisted[_referral]) { rewards[_referral] += toRef; rewards[authority.guardian()] += toDAO; } else { // the DAO receives both rewards if referrer is not whitelisted rewards[authority.guardian()] += toDAO + toRef; } return toDAO + toRef; } /** * @notice set rewards for front end operators and DAO */ function setRewards(uint256 _toFrontEnd, uint256 _toDAO) external onlyGovernor { refReward = _toFrontEnd; daoReward = _toDAO; emit SetRewards(_toFrontEnd, _toDAO); } /** * @notice add or remove addresses from the reward whitelist */ function whitelist(address _operator) external onlyPolicy { whitelisted[_operator] = !whitelisted[_operator]; } }
// SPDX-License-Identifier: AGPL-3.0-only pragma solidity ^0.8.10; import "./FrontEndRewarder.sol"; import "../Interfaces/IStakedTHEOToken.sol"; import "../Interfaces/IStaking.sol"; import "../Interfaces/ITreasury.sol"; import "../Interfaces/INoteKeeper.sol"; abstract contract NoteKeeper is INoteKeeper, FrontEndRewarder { mapping(address => Note[]) public notes; // user deposit data mapping(address => mapping(uint256 => address)) private noteTransfers; // change note ownership mapping(address => mapping(uint256 => uint256)) private noteForClaim; // index of staking claim for a user's note event TreasuryUpdated(address addr); event PushNote(address from, address to, uint256 noteId); event PullNote(address from, address to, uint256 noteId); IStakedTHEOToken internal immutable sTHEO; IStaking internal immutable staking; ITreasury internal treasury; constructor( ITheopetraAuthority _authority, IERC20 _theo, IStakedTHEOToken _stheo, IStaking _staking, ITreasury _treasury ) FrontEndRewarder(_authority, _theo) { sTHEO = _stheo; staking = _staking; treasury = _treasury; } // if treasury address changes on authority, update it function updateTreasury() external { require( msg.sender == authority.governor() || msg.sender == authority.guardian() || msg.sender == authority.policy(), "Only authorized" ); address treasuryAddress = authority.vault(); treasury = ITreasury(treasuryAddress); emit TreasuryUpdated(treasuryAddress); } /* ========== ADD ========== */ /** * @notice adds a new Note for a user, stores the front end & DAO rewards, and mints & stakes payout & rewards * @param _user the user that owns the Note * @param _payout the amount of THEO due to the user * @param _expiry the timestamp when the Note is redeemable * @param _marketID the ID of the market deposited into * @param _discount the discount on the bond (that is, the bond rate, variable). This is a proportion (that is, a percentage in its decimal form), with 9 decimals * @return index_ the index of the Note in the user's array */ function addNote( address _user, uint256 _payout, uint48 _expiry, uint48 _marketID, address _referral, uint48 _discount, bool _autoStake ) internal returns (uint256 index_) { // the index of the note is the next in the user's array index_ = notes[_user].length; // the new note is pushed to the user's array notes[_user].push( Note({ payout: _payout, created: uint48(block.timestamp), matured: _expiry, redeemed: 0, marketID: _marketID, discount: _discount, autoStake: _autoStake }) ); // front end operators can earn rewards by referring users uint256 rewards = _giveRewards(_payout, _referral); // mint and stake payout treasury.mint(address(this), _payout + rewards); if (_autoStake) { // note that only the payout gets staked (front end rewards are in THEO) // Get index for the claim to approve for pushing (, uint256 claimIndex) = staking.stake(address(this), _payout, true); // approve the user to transfer the staking claim staking.pushClaim(_user, claimIndex); // Map the index of the user's note to the claimIndex noteForClaim[_user][index_] = claimIndex; } } /* ========== REDEEM ========== */ /** * @notice redeem notes for user * @dev adapted from Olympus V2. Olympus V2 either sends payout as gOHM * or calls an `unwrap` function on the staking contract * to convert the payout from gOHM into sOHM and then send as sOHM. * This current contract sends payout as sTHEO. * @param _user the user to redeem for * @param _indexes the note indexes to redeem * @return payout_ sum of payout sent, in sTHEO */ function redeem(address _user, uint256[] memory _indexes) public override returns (uint256 payout_) { uint48 time = uint48(block.timestamp); uint256 sTheoPayout = 0; uint256 theoPayout = 0; for (uint256 i = 0; i < _indexes.length; i++) { (uint256 pay, , , , bool matured, ) = pendingFor(_user, _indexes[i]); if (matured) { notes[_user][_indexes[i]].redeemed = time; // mark as redeemed payout_ += pay; if (notes[_user][_indexes[i]].autoStake) { uint256 _claimIndex = noteForClaim[_user][_indexes[i]]; staking.pushClaimForBond(_user, _claimIndex); sTheoPayout += pay; } else { theoPayout += pay; } } } if (theoPayout > 0) theo.transfer(_user, theoPayout); if (sTheoPayout > 0) sTHEO.transfer(_user, sTheoPayout); } /** * @notice redeem all redeemable markets for user * @dev if possible, query indexesFor() off-chain and input in redeem() to save gas * @param _user user to redeem all notes for * @return sum of payout sent, in sTHEO */ function redeemAll(address _user) external override returns (uint256) { return redeem(_user, indexesFor(_user)); } /* ========== TRANSFER ========== */ /** * @notice approve an address to transfer a note * @param _to address to approve note transfer for * @param _index index of note to approve transfer for */ function pushNote(address _to, uint256 _index) external override { require(notes[msg.sender][_index].created != 0, "Depository: note not found"); noteTransfers[msg.sender][_index] = _to; emit PushNote(msg.sender, _to, _index); } /** * @notice transfer a note that has been approved by an address * @dev if the note being pulled is autostaked then update noteForClaim as follows: * get the relevant `claimIndex` associated with the note that is being pulled. * Then add the claimIndex to the recipient's noteForClaim. * After updating noteForClaim, the staking claim is pushed to the recipient, in order to * update `claimTransfers` in the Staking contract and thereby change claim ownership (from the note's pusher to the note's recipient) * @param _from the address that approved the note transfer * @param _index the index of the note to transfer (in the sender's array) */ function pullNote(address _from, uint256 _index) external override returns (uint256 newIndex_) { require(noteTransfers[_from][_index] == msg.sender, "Depository: transfer not found"); require(notes[_from][_index].redeemed == 0, "Depository: note redeemed"); newIndex_ = notes[msg.sender].length; if (notes[_from][_index].autoStake) { uint256 claimIndex = noteForClaim[_from][_index]; noteForClaim[msg.sender][newIndex_] = claimIndex; staking.pushClaim(msg.sender, claimIndex); } notes[msg.sender].push(notes[_from][_index]); delete notes[_from][_index]; emit PullNote(_from, msg.sender, _index); } /* ========== VIEW ========== */ // Note info /** * @notice all pending notes for user * @param _user the user to query notes for * @return the pending notes for the user */ function indexesFor(address _user) public view override returns (uint256[] memory) { Note[] memory info = notes[_user]; uint256 length; for (uint256 i = 0; i < info.length; i++) { if (info[i].redeemed == 0 && info[i].payout != 0) length++; } uint256[] memory indexes = new uint256[](length); uint256 position; for (uint256 i = 0; i < info.length; i++) { if (info[i].redeemed == 0 && info[i].payout != 0) { indexes[position] = i; position++; } } return indexes; } /** * @notice calculate amount available for claim for a single note * @param _user the user that the note belongs to * @param _index the index of the note in the user's array * @return payout_ the payout due, in sTHEO * @return created_ the time the note was created * @return expiry_ the time the note is redeemable * @return timeRemaining_ the time remaining until the note is matured * @return matured_ if the payout can be redeemed */ function pendingFor(address _user, uint256 _index) public view override returns ( uint256 payout_, uint48 created_, uint48 expiry_, uint48 timeRemaining_, bool matured_, uint48 discount_ ) { Note memory note = notes[_user][_index]; payout_ = note.payout; created_ = note.created; expiry_ = note.matured; timeRemaining_ = note.matured > block.timestamp ? uint48(note.matured - block.timestamp) : 0; matured_ = note.redeemed == 0 && note.matured <= block.timestamp && note.payout != 0; discount_ = note.discount; } function getNotesCount(address _user) external view returns (uint256) { return notes[_user].length; } }
// SPDX-License-Identifier: AGPL-3.0 pragma solidity ^0.8.9; import "@chainlink/contracts/src/v0.8/interfaces/AggregatorV3Interface.sol"; contract PriceConsumerV3 { /** * Returns the latest price */ function getLatestPrice(address priceFeedAddress) public view returns (int256, uint8) { ( uint80 roundID, int256 price, uint256 startedAt, uint256 timeStamp, uint80 answeredInRound ) = AggregatorV3Interface(priceFeedAddress).latestRoundData(); uint8 decimals = AggregatorV3Interface(priceFeedAddress).decimals(); return (price, decimals); } }
// SPDX-License-Identifier: BSD-3 pragma solidity ^0.8.0; import "@openzeppelin/contracts/utils/Strings.sol"; import "@openzeppelin/contracts/utils/cryptography/ECDSA.sol"; import "./TheopetraAccessControlled.sol"; abstract contract Signed is TheopetraAccessControlled { using Strings for uint256; using ECDSA for bytes32; string private _secret; event SetSecret(string secret); function setSecret(string calldata secret) external onlyGovernor { _secret = secret; emit SetSecret(secret); } function createHash(string memory data) internal view returns (bytes32) { return keccak256(abi.encodePacked(address(this), msg.sender, data, _secret)); } function getSigner(bytes32 hash, bytes memory signature) internal pure returns (address) { return hash.toEthSignedMessageHash().recover(signature); } function isAuthorizedSigner(address extracted) internal view virtual returns (bool) { return extracted == authority.whitelistSigner(); } function verifySignature(string memory data, bytes calldata signature) internal view { address extracted = getSigner(createHash(data), signature); require(isAuthorizedSigner(extracted), "Signature verification failed"); } }
// SPDX-License-Identifier: AGPL-3.0-only pragma solidity >=0.7.5; import "../Interfaces/ITheopetraAuthority.sol"; abstract contract TheopetraAccessControlled { /* ========== EVENTS ========== */ event AuthorityUpdated(ITheopetraAuthority indexed authority); string constant UNAUTHORIZED = "UNAUTHORIZED"; // save gas /* ========== STATE VARIABLES ========== */ ITheopetraAuthority public authority; /* ========== Constructor ========== */ constructor(ITheopetraAuthority _authority) { authority = _authority; emit AuthorityUpdated(_authority); } /* ========== MODIFIERS ========== */ modifier onlyGovernor() { require(msg.sender == authority.governor(), UNAUTHORIZED); _; } modifier onlyGuardian() { require(msg.sender == authority.guardian(), UNAUTHORIZED); _; } modifier onlyPolicy() { require(msg.sender == authority.policy(), UNAUTHORIZED); _; } modifier onlyManager() { require(msg.sender == authority.manager(), UNAUTHORIZED); _; } modifier onlyVault() { require(msg.sender == authority.vault(), UNAUTHORIZED); _; } /* ========== GOV ONLY ========== */ function setAuthority(ITheopetraAuthority _newAuthority) external onlyGovernor { authority = _newAuthority; emit AuthorityUpdated(_newAuthority); } }
{ "evmVersion": "london", "libraries": {}, "metadata": { "bytecodeHash": "ipfs", "useLiteralContent": true }, "optimizer": { "enabled": true, "runs": 2000 }, "remappings": [], "outputSelection": { "*": { "*": [ "evm.bytecode", "evm.deployedBytecode", "devdoc", "userdoc", "metadata", "abi" ] } } }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
[{"inputs":[{"internalType":"contract ITheopetraAuthority","name":"_authority","type":"address"},{"internalType":"contract IERC20","name":"_theo","type":"address"},{"internalType":"contract IStakedTHEOToken","name":"_stheo","type":"address"},{"internalType":"contract IStaking","name":"_staking","type":"address"},{"internalType":"contract ITreasury","name":"_treasury","type":"address"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"contract ITheopetraAuthority","name":"authority","type":"address"}],"name":"AuthorityUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"id","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"price","type":"uint256"}],"name":"Bond","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"id","type":"uint256"}],"name":"CloseMarket","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"id","type":"uint256"},{"indexed":true,"internalType":"address","name":"baseToken","type":"address"},{"indexed":true,"internalType":"address","name":"quoteToken","type":"address"},{"indexed":false,"internalType":"uint256","name":"fixedBondPrice","type":"uint256"}],"name":"CreateMarket","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"from","type":"address"},{"indexed":false,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"noteId","type":"uint256"}],"name":"PullNote","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"from","type":"address"},{"indexed":false,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"noteId","type":"uint256"}],"name":"PushNote","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"uint256","name":"toRef","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"toDao","type":"uint256"}],"name":"SetRewards","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"string","name":"secret","type":"string"}],"name":"SetSecret","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"addr","type":"address"}],"name":"TreasuryUpdated","type":"event"},{"inputs":[],"name":"authority","outputs":[{"internalType":"contract ITheopetraAuthority","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_id","type":"uint256"}],"name":"calculatePrice","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_id","type":"uint256"}],"name":"close","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"contract IERC20","name":"_quoteToken","type":"address"},{"internalType":"address","name":"_priceFeed","type":"address"},{"internalType":"uint256[2]","name":"_market","type":"uint256[2]"},{"internalType":"bool[2]","name":"_booleans","type":"bool[2]"},{"internalType":"uint256[2]","name":"_terms","type":"uint256[2]"}],"name":"create","outputs":[{"internalType":"uint256","name":"id_","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"daoReward","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_id","type":"uint256"},{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"uint256","name":"_maxPrice","type":"uint256"},{"internalType":"address","name":"_user","type":"address"},{"internalType":"address","name":"_referral","type":"address"},{"internalType":"bytes","name":"signature","type":"bytes"}],"name":"deposit","outputs":[{"components":[{"internalType":"uint256","name":"payout_","type":"uint256"},{"internalType":"uint256","name":"expiry_","type":"uint256"},{"internalType":"uint256","name":"index_","type":"uint256"}],"internalType":"struct IWhitelistBondDepository.DepositInfo","name":"depositInfo","type":"tuple"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"priceFeedAddress","type":"address"}],"name":"getLatestPrice","outputs":[{"internalType":"int256","name":"","type":"int256"},{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getMarkets","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_token","type":"address"}],"name":"getMarketsFor","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_user","type":"address"}],"name":"getNotesCount","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getReward","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_user","type":"address"}],"name":"indexesFor","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_id","type":"uint256"}],"name":"isLive","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"liveMarkets","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_token","type":"address"}],"name":"liveMarketsFor","outputs":[{"internalType":"uint256[]","name":"","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"markets","outputs":[{"internalType":"uint256","name":"capacity","type":"uint256"},{"internalType":"contract IERC20","name":"quoteToken","type":"address"},{"internalType":"address","name":"priceFeed","type":"address"},{"internalType":"bool","name":"capacityInQuote","type":"bool"},{"internalType":"uint64","name":"sold","type":"uint64"},{"internalType":"uint256","name":"purchased","type":"uint256"},{"internalType":"uint256","name":"usdPricePerTHEO","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"}],"name":"marketsForQuote","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"metadata","outputs":[{"internalType":"uint8","name":"quoteDecimals","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"},{"internalType":"uint256","name":"","type":"uint256"}],"name":"notes","outputs":[{"internalType":"uint256","name":"payout","type":"uint256"},{"internalType":"uint48","name":"created","type":"uint48"},{"internalType":"uint48","name":"matured","type":"uint48"},{"internalType":"uint48","name":"redeemed","type":"uint48"},{"internalType":"uint48","name":"marketID","type":"uint48"},{"internalType":"uint48","name":"discount","type":"uint48"},{"internalType":"bool","name":"autoStake","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"_amount","type":"uint256"},{"internalType":"uint256","name":"_id","type":"uint256"}],"name":"payoutFor","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_user","type":"address"},{"internalType":"uint256","name":"_index","type":"uint256"}],"name":"pendingFor","outputs":[{"internalType":"uint256","name":"payout_","type":"uint256"},{"internalType":"uint48","name":"created_","type":"uint48"},{"internalType":"uint48","name":"expiry_","type":"uint48"},{"internalType":"uint48","name":"timeRemaining_","type":"uint48"},{"internalType":"bool","name":"matured_","type":"bool"},{"internalType":"uint48","name":"discount_","type":"uint48"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_from","type":"address"},{"internalType":"uint256","name":"_index","type":"uint256"}],"name":"pullNote","outputs":[{"internalType":"uint256","name":"newIndex_","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_to","type":"address"},{"internalType":"uint256","name":"_index","type":"uint256"}],"name":"pushNote","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_user","type":"address"},{"internalType":"uint256[]","name":"_indexes","type":"uint256[]"}],"name":"redeem","outputs":[{"internalType":"uint256","name":"payout_","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_user","type":"address"}],"name":"redeemAll","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"refReward","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"rewards","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"contract ITheopetraAuthority","name":"_newAuthority","type":"address"}],"name":"setAuthority","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"_toFrontEnd","type":"uint256"},{"internalType":"uint256","name":"_toDAO","type":"uint256"}],"name":"setRewards","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"secret","type":"string"}],"name":"setSecret","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_wethHelper","type":"address"}],"name":"setWethHelper","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"terms","outputs":[{"internalType":"bool","name":"fixedTerm","type":"bool"},{"internalType":"uint48","name":"vesting","type":"uint48"},{"internalType":"uint48","name":"conclusion","type":"uint48"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"updateTreasury","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"_operator","type":"address"}],"name":"whitelist","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"whitelisted","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"}]
Contract Creation Code
60e06040523480156200001157600080fd5b506040516200493638038062004936833981016040819052620000349162000164565b600080546001600160a01b0319166001600160a01b038716908117825560405187928792879287928792879287928492917f2f658b440c35314f52658ea8a740e05b284cdc84dc9ae01e891f21b8933e7cad9190a2506001600160a01b0390811660805293841660a0525090821660c052600880546001600160a01b03191691831691909117905560405163095ea7b360e01b81528582166004820152722cd76fe086b93ce2f768a00b22a000000000006024820152908716925063095ea7b391506044016020604051808303816000875af115801562000119573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200013f9190620001e4565b5050505050506200020f565b6001600160a01b03811681146200016157600080fd5b50565b600080600080600060a086880312156200017d57600080fd5b85516200018a816200014b565b60208701519095506200019d816200014b565b6040870151909450620001b0816200014b565b6060870151909350620001c3816200014b565b6080870151909250620001d6816200014b565b809150509295509295909350565b600060208284031215620001f757600080fd5b815180151581146200020857600080fd5b9392505050565b60805160a05160c0516146d46200026260003960008181611e4f015281816126a3015281816131b1015261326701526000612843015260008181610a640152818161184e01526127a801526146d46000f3fe608060405234801561001057600080fd5b50600436106102415760003560e01c8063ae10426511610145578063d2390aa2116100bd578063e3684e391161008c578063e4994e9611610071578063e4994e9614610637578063ec2c90161461064a578063f3191a461461065257600080fd5b8063e3684e39146105ff578063e481b2651461062457600080fd5b8063d2390aa21461055d578063d6db4df814610570578063d936547e14610583578063e0b117ff146105a657600080fd5b8063bf7e214f11610114578063c0aa0e8a116100f9578063c0aa0e8a146104cc578063c3e0fb1c14610505578063c9b67af51461055557600080fd5b8063bf7e214f1461048e578063c0680e20146104b957600080fd5b8063ae104265146103e1578063b1283e77146103f4578063b6d8eee014610452578063be399be51461047b57600080fd5b8063654e51e7116101d8578063964561c4116101a75780639b19251a1161018c5780639b19251a146103b35780639c769787146103c6578063a4220610146103ce57600080fd5b8063964561c41461036b5780639a1e46d5146103a057600080fd5b8063654e51e71461031f5780636a6c575d146103325780637a9e5e4b146103455780637ed6c9261461035857600080fd5b8063275074581161021457806327507458146102c1578063333d7d77146102e45780633d18b91214610304578063649144391461030c57600080fd5b80630700037d146102465780630aebeb4e1461027957806316345f181461028e5780631885f580146102b8575b600080fd5b610266610254366004613c63565b60036020526000908152604090205481565b6040519081526020015b60405180910390f35b61028c610287366004613c80565b61065b565b005b6102a161029c366004613c63565b6107c7565b6040805192835260ff909116602083015201610270565b61026660015481565b6102d46102cf366004613c80565b6108b2565b6040519015158152602001610270565b6102f76102f2366004613c63565b61091f565b6040516102709190613c99565b61028c610a2a565b6102f761031a366004613c63565b610ad5565b61028c61032d366004613cdd565b610c64565b610266610340366004613cdd565b610d79565b61028c610353366004613c63565b610df0565b61028c610366366004613d41565b610f12565b61037e610379366004613d83565b61101d565b6040805182518152602080840151908201529181015190820152606001610270565b6102666103ae366004613ecc565b611401565b61028c6103c1366004613c63565b6118a5565b61028c61199b565b6102666103dc366004613f7e565b611c6c565b6102666103ef366004613c80565b61215d565b610407610402366004613c80565b6121f4565b604080519788526001600160a01b0396871660208901529490951693860193909352901515606085015267ffffffffffffffff16608084015260a083015260c082015260e001610270565b610266610460366004613c63565b6001600160a01b031660009081526005602052604090205490565b610266610489366004613c63565b612272565b6000546104a1906001600160a01b031681565b6040516001600160a01b039091168152602001610270565b6102666104c7366004613f7e565b612281565b6104df6104da366004613c80565b6122b2565b60408051931515845265ffffffffffff9283166020850152911690820152606001610270565b610518610513366004613f7e565b6122f2565b6040805196875265ffffffffffff9586166020880152938516938601939093529083166060850152151560808401521660a082015260c001610270565b6102f761243b565b61026661056b366004613faa565b612524565b61028c61057e366004613f7e565b6128bb565b6102d4610591366004613c63565b60046020526000908152604090205460ff1681565b6105b96105b4366004613f7e565b6129c0565b6040805197885265ffffffffffff96871660208901529486169487019490945291841660608601528316608085015290911660a0830152151560c082015260e001610270565b61061261060d366004613c80565b612a45565b60405160ff9091168152602001610270565b6102f7610632366004613c63565b612a69565b61028c610645366004613c63565b612cba565b6102f7612e0c565b61026660025481565b60008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa1580156106ac573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106d09190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906107305760405162461bcd60e51b815260040161072791906140ae565b60405180910390fd5b5042600b8281548110610745576107456140e1565b9060005260206000200160000160076101000a81548165ffffffffffff021916908365ffffffffffff1602179055506000600a8281548110610789576107896140e1565b6000918252602082206005909102019190915560405182917f8401d05adbea6548a6999cc1540766e6d2ff919292142862893d0e62ec79fbe591a250565b6000806000806000806000876001600160a01b031663feaf968c6040518163ffffffff1660e01b815260040160a060405180830381865afa158015610810573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108349190614116565b945094509450945094506000886001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa15801561087e573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108a29190614166565b9499949850939650505050505050565b6000600a82815481106108c7576108c76140e1565b906000526020600020906005020160000154600014158015610919575042600b83815481106108f8576108f86140e1565b600091825260209091200154670100000000000000900465ffffffffffff16115b92915050565b6001600160a01b0381166000908152600e6020908152604080832080548251818502810185019093528083526060949383018282801561097e57602002820191906000526020600020905b81548152602001906001019080831161096a575b505050505090506000815167ffffffffffffffff8111156109a1576109a1613e09565b6040519080825280602002602001820160405280156109ca578160200160208202803683370190505b50905060005b8251811015610a22578281815181106109eb576109eb6140e1565b6020026020010151828281518110610a0557610a056140e1565b602090810291909101015280610a1a8161419f565b9150506109d0565b509392505050565b3360008181526003602052604080822080549290555163a9059cbb60e01b8152600481019290925260248201819052906001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169063a9059cbb906044016020604051808303816000875af1158015610aad573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad191906141ba565b5050565b6001600160a01b0381166000908152600e60209081526040808320805482518185028101850190935280835260609493830182828015610b3457602002820191906000526020600020905b815481526020019060010190808311610b20575b50505050509050600080600090505b8251811015610b9357610b6e838281518110610b6157610b616140e1565b60200260200101516108b2565b15610b815781610b7d8161419f565b9250505b80610b8b8161419f565b915050610b43565b5060008167ffffffffffffffff811115610baf57610baf613e09565b604051908082528060200260200182016040528015610bd8578160200160208202803683370190505b5090506000805b8451811015610c5957610bfd858281518110610b6157610b616140e1565b15610c4757848181518110610c1457610c146140e1565b6020026020010151838381518110610c2e57610c2e6140e1565b602090810291909101015281610c438161419f565b9250505b80610c518161419f565b915050610bdf565b509095945050505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610cb5573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610cd99190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610d305760405162461bcd60e51b815260040161072791906140ae565b506002829055600181905560408051838152602081018390527f41ddb6f76c2aab8405d1cca4bd752e126ac8976c1203888790f8594c7ba3661191015b60405180910390a15050565b600080600c8381548110610d8f57610d8f6140e1565b6000918252602091829020604080519384019052015460ff16808252909150610db990600a6142bb565b610dc28461215d565b610dd486670de0b6b3a76400006142ca565b610dde91906142ff565b610de891906142ff565b949350505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610e41573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610e659190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610ebc5760405162461bcd60e51b815260040161072791906140ae565b506000805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b038316908117825560405190917f2f658b440c35314f52658ea8a740e05b284cdc84dc9ae01e891f21b8933e7cad91a250565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610f63573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610f879190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610fde5760405162461bcd60e51b815260040161072791906140ae565b50610feb60098383613bb5565b507fc84ba0d041142642d7c555ad8e697a8d84a7bc3fdf46d377be42ef3ad71b5eda8282604051610d6d929190614313565b61104160405180606001604052806000815260200160008152602001600081525090565b600d546001600160a01b0316331461106d5761106d604051806020016040528060008152508484612e9c565b6000600a8981548110611082576110826140e1565b906000526020600020906005020190506000600b8a815481106110a7576110a76140e1565b600091825260209182902060408051606081018252919092015460ff81161515825265ffffffffffff610100820481169483019490945267010000000000000090048316918101829052925042918216106111445760405162461bcd60e51b815260206004820152601c60248201527f4465706f7369746f72793a206d61726b657420636f6e636c75646564000000006044820152606401610727565b600061114f8c61215d565b9050898111156111a15760405162461bcd60e51b815260206004820152601f60248201527f4465706f7369746f72793a206d6f7265207468616e206d6178207072696365006044820152606401610727565b600c8c815481106111b4576111b46140e1565b6000918252602090912001546111ce9060ff16600a6142bb565b816111e18d670de0b6b3a76400006142ca565b6111eb91906142ff565b6111f591906142ff565b85526002840154600160a01b900460ff16611211578451611213565b8a5b845410156112635760405162461bcd60e51b815260206004820152601d60248201527f4465706f7369746f72793a2063617061636974792065786365656465640000006044820152606401610727565b6002840154600160a01b900460ff1661127d57845161127f565b8a5b8460000160008282546112929190614342565b909155505083546112c9576040518c907f8401d05adbea6548a6999cc1540766e6d2ff919292142862893d0e62ec79fbe590600090a25b82516112d95782602001516112e9565b8183602001516112e99190614359565b65ffffffffffff1660208601526003840180548c919060009061130d908490614383565b9091555050845160028501805460159061134b9084907501000000000000000000000000000000000000000000900467ffffffffffffffff1661439b565b92506101000a81548167ffffffffffffffff021916908367ffffffffffffffff1602179055508b7f7880508a48fd3aee88f7e15917d85e39c3ad059e51ad4aca9bb46e7b4938b9618c836040516113ac929190918252602082015260400190565b60405180910390a26113cc89866000015187602001518f8c600080612f43565b604086015260085460018501546113f2916001600160a01b03918216913391168e6132f7565b50505050979650505050505050565b60008060009054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa158015611455573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114799190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906114d05760405162461bcd60e51b815260040161072791906140ae565b506000866001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa158015611511573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906115359190614166565b60ff169050600a805490509150600a6040518060e0016040528087600060028110611562576115626140e1565b60200201518152602001896001600160a01b03168152602001886001600160a01b031681526020018660006002811061159d5761159d6140e1565b602002015115158152602001600067ffffffffffffffff16815260200160008152602001876001600281106115d4576115d46140e1565b60209081029190910151909152825460018082018555600094855282852084516005909302019182558383015182820180546001600160a01b0392831673ffffffffffffffffffffffffffffffffffffffff199091161790556040808601516002850180546060808a015160808b015167ffffffffffffffff167501000000000000000000000000000000000000000000027fffffff0000000000000000ffffffffffffffffffffffffffffffffffffffffff911515600160a01b027fffffffffffffffffffffff00000000000000000000000000000000000000000090941695881695909517929092179190911692909217905560a0870151600386015560c090960151600490940193909355825194850183528984015115158552885165ffffffffffff9081168686019081528a8601518216878601908152600b80548087018255908a5297517f0175b7a638427703f0dbe7bb9bbf987a2551717b34e79f33b5b1008d1fa01db99098018054925191517fffffffffffffffffffffffffffffffffffffffffffffffffff000000000000009093169815157fffffffffffffffffffffffffffffffffffffffffffffffffff000000000000ff169890981761010091841691909102177fffffffffffffffffffffffffffffffffffffff000000000000ffffffffffffff166701000000000000009190921602179094558151808401835260ff8781168252600c8054808501825590885291517fdf6966c971051c3d54ec59162606531493a51404a002842f56009d7e5cf4a8c7909201805460ff1916929091169190911790558b8416808652600e8452828620805492830181558652948390200186905588820151815190815290517f00000000000000000000000000000000000000000000000000000000000000009093169286927f2f6ff727bd580b1d1b8332e28aa93ed4ec9d8b08d6e30d6b4c9f7aa63ca17f63928290030190a45095945050505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa1580156118f6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061191a9190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906119715760405162461bcd60e51b815260040161072791906140ae565b506001600160a01b03166000908152600460205260409020805460ff19811660ff90911615179055565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa1580156119ec573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a109190614065565b6001600160a01b0316336001600160a01b03161480611ab4575060008054906101000a90046001600160a01b03166001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015611a7b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a9f9190614065565b6001600160a01b0316336001600160a01b0316145b80611b44575060008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa158015611b0b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b2f9190614065565b6001600160a01b0316336001600160a01b0316145b611b905760405162461bcd60e51b815260206004820152600f60248201527f4f6e6c7920617574686f72697a656400000000000000000000000000000000006044820152606401610727565b60008060009054906101000a90046001600160a01b03166001600160a01b031663fbfa77cf6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611be4573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c089190614065565b6008805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0383169081179091556040519081529091507f7dae230f18360d76a040c81f050aa14eb9d6dc7901b20fc5d855e2a20fe814d19060200160405180910390a150565b6001600160a01b0382811660009081526006602090815260408083208584529091528120549091163314611ce25760405162461bcd60e51b815260206004820152601e60248201527f4465706f7369746f72793a207472616e73666572206e6f7420666f756e6400006044820152606401610727565b6001600160a01b0383166000908152600560205260409020805483908110611d0c57611d0c6140e1565b60009182526020909120600290910201600101546c01000000000000000000000000900465ffffffffffff1615611d855760405162461bcd60e51b815260206004820152601960248201527f4465706f7369746f72793a206e6f74652072656465656d6564000000000000006044820152606401610727565b5033600090815260056020526040808220546001600160a01b03851683529120805483908110611db757611db76140e1565b9060005260206000209060020201600101601e9054906101000a900460ff1615611ead576001600160a01b038381166000908152600760208181526040808420878552825280842054338086529383528185208786529092529283902081905591517f78f1f77800000000000000000000000000000000000000000000000000000000815260048101919091526024810182905290917f000000000000000000000000000000000000000000000000000000000000000016906378f1f77890604401600060405180830381600087803b158015611e9357600080fd5b505af1158015611ea7573d6000803e3d6000fd5b50505050505b336000908152600560205260408082206001600160a01b03861683529120805484908110611edd57611edd6140e1565b60009182526020808320845460018181018755958552828520600294850290920180549190940290910190815591840180549290940180547fffffffffffffffffffffffffffffffffffffffffffffffffffff000000000000811665ffffffffffff948516908117835586546601000000000000908190048616026bffffffffffffffffffffffff19909216171780825585546c01000000000000000000000000908190048516027fffffffffffffffffffffffffffff000000000000ffffffffffffffffffffffff8216811783558654600160901b908190048616027fffffffffffffffff000000000000ffffffffffffffffffffffffffffffffffff9091167fffffffffffffffff000000000000000000000000ffffffffffffffffffffffff90921691909117178082558554600160c01b908190049094169093027fffff000000000000ffffffffffffffffffffffffffffffffffffffffffffffff841681178255945460ff600160f01b91829004161515027fff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff9095167fff00000000000000ffffffffffffffffffffffffffffffffffffffffffffffff909316929092179390931790556001600160a01b03851681526005909152604090208054839081106120cc576120cc6140e1565b60009182526020808320600292909202909101918255600190910180547fff00000000000000000000000000000000000000000000000000000000000000169055604080516001600160a01b0386168152339281019290925281018390527fac662197bb43cbfbf62b5caf539eb823ba3ee6f13941f9978304958a2c916ebf9060600160405180910390a192915050565b600080600061219a600a8581548110612178576121786140e1565b60009182526020909120600260059092020101546001600160a01b03166107c7565b9150915060006121dc600a86815481106121b6576121b66140e1565b90600052602060002090600502016004015460098460096121d791906143be565b613449565b905060006121ea84836143e3565b9695505050505050565b600a818154811061220457600080fd5b6000918252602090912060059091020180546001820154600283015460038401546004909401549294506001600160a01b039182169391811692600160a01b820460ff1692750100000000000000000000000000000000000000000090920467ffffffffffffffff16919087565b60006109198261056b84612a69565b600e602052816000526040600020818154811061229d57600080fd5b90600052602060002001600091509150505481565b600b81815481106122c257600080fd5b60009182526020909120015460ff8116915065ffffffffffff610100820481169167010000000000000090041683565b6000806000806000806000600560008a6001600160a01b03166001600160a01b031681526020019081526020016000208881548110612333576123336140e1565b60009182526020918290206040805160e0810182526002909302909101805480845260019091015465ffffffffffff8082169585018690526601000000000000820481169385018490526c01000000000000000000000000820481166060860152600160901b820481166080860152600160c01b82041660a085015260ff600160f01b90910416151560c0840152995091975090955090504285116123d95760006123f1565b42816040015165ffffffffffff166123f19190614342565b9350806060015165ffffffffffff16600014801561241b575042816040015165ffffffffffff1611155b80156124275750805115155b92508060a001519150509295509295509295565b60606000805b600a5481101561247957612454816108b2565b1561246757816124638161419f565b9250505b806124718161419f565b915050612441565b5060008167ffffffffffffffff81111561249557612495613e09565b6040519080825280602002602001820160405280156124be578160200160208202803683370190505b5090506000805b600a5481101561251b576124d8816108b2565b1561250957808383815181106124f0576124f06140e1565b6020908102919091010152816125058161419f565b9250505b806125138161419f565b9150506124c5565b50909392505050565b6000428180805b855181101561277b5760008061255a8989858151811061254d5761254d6140e1565b60200260200101516122f2565b50945050505091508015612766576001600160a01b038916600090815260056020526040902088518791908a9086908110612597576125976140e1565b6020026020010151815481106125af576125af6140e1565b9060005260206000209060020201600101600c6101000a81548165ffffffffffff021916908365ffffffffffff16021790555081876125ee9190614383565b6001600160a01b038a16600090815260056020526040902089519198509089908590811061261e5761261e6140e1565b602002602001015181548110612636576126366140e1565b9060005260206000209060020201600101601e9054906101000a900460ff1615612759576001600160a01b0389166000908152600760205260408120895182908b9087908110612688576126886140e1565b602002602001015181526020019081526020016000205490507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b031663b3e504098b836040518363ffffffff1660e01b81526004016127039291906001600160a01b03929092168252602082015260400190565b6020604051808303816000875af1158015612722573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612746919061442d565b506127518387614383565b955050612766565b6127638285614383565b93505b505080806127739061419f565b91505061252b565b5080156128175760405163a9059cbb60e01b81526001600160a01b038781166004830152602482018390527f0000000000000000000000000000000000000000000000000000000000000000169063a9059cbb906044016020604051808303816000875af11580156127f1573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061281591906141ba565b505b81156128b25760405163a9059cbb60e01b81526001600160a01b038781166004830152602482018490527f0000000000000000000000000000000000000000000000000000000000000000169063a9059cbb906044016020604051808303816000875af115801561288c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906128b091906141ba565b505b50505092915050565b3360009081526005602052604090208054829081106128dc576128dc6140e1565b600091825260209091206001600290920201015465ffffffffffff166129445760405162461bcd60e51b815260206004820152601a60248201527f4465706f7369746f72793a206e6f7465206e6f7420666f756e640000000000006044820152606401610727565b336000818152600660209081526040808320858452825291829020805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b03871690811790915582519384529083015281018290527f46a855c725ecb3b899b429c361a8e87ced35203a422c4324e83b6a43b0b70c2390606001610d6d565b600560205281600052604060002081815481106129dc57600080fd5b60009182526020909120600290910201805460019091015490925065ffffffffffff8082169250660100000000000082048116916c010000000000000000000000008104821691600160901b8204811691600160c01b810490911690600160f01b900460ff1687565b600c8181548110612a5557600080fd5b60009182526020909120015460ff16905081565b6001600160a01b0381166000908152600560209081526040808320805482518185028101850190935280835260609493849084015b82821015612b405760008481526020908190206040805160e081018252600286029092018054835260019081015465ffffffffffff80821685870152660100000000000082048116938501939093526c01000000000000000000000000810483166060850152600160901b810483166080850152600160c01b810490921660a0840152600160f01b90910460ff16151560c08301529083529092019101612a9e565b505050509050600080600090505b8251811015612bcf57828181518110612b6957612b696140e1565b60200260200101516060015165ffffffffffff166000148015612baa5750828181518110612b9957612b996140e1565b602002602001015160000151600014155b15612bbd5781612bb98161419f565b9250505b80612bc78161419f565b915050612b4e565b5060008167ffffffffffffffff811115612beb57612beb613e09565b604051908082528060200260200182016040528015612c14578160200160208202803683370190505b5090506000805b8451811015610c5957848181518110612c3657612c366140e1565b60200260200101516060015165ffffffffffff166000148015612c775750848181518110612c6657612c666140e1565b602002602001015160000151600014155b15612ca85780838381518110612c8f57612c8f6140e1565b602090810291909101015281612ca48161419f565b9250505b80612cb28161419f565b915050612c1b565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015612d0b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612d2f9190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090612d865760405162461bcd60e51b815260040161072791906140ae565b506001600160a01b038116612ddd5760405162461bcd60e51b815260206004820152600c60248201527f5a65726f206164647265737300000000000000000000000000000000000000006044820152606401610727565b600d805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0392909216919091179055565b600a5460609060009067ffffffffffffffff811115612e2d57612e2d613e09565b604051908082528060200260200182016040528015612e56578160200160208202803683370190505b50905060005b600a54811015612e965780828281518110612e7957612e796140e1565b602090810291909101015280612e8e8161419f565b915050612e5c565b50919050565b6000612ee6612eaa856134bc565b84848080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506134f392505050565b9050612ef181613508565b612f3d5760405162461bcd60e51b815260206004820152601d60248201527f5369676e617475726520766572696669636174696f6e206661696c65640000006044820152606401610727565b50505050565b6001600160a01b03871660009081526005602090815260408083208054825160e0810184528b815265ffffffffffff4281168287019081528c8216958301958652606083018881528c8316608085019081528b841660a086019081528b151560c0870190815260018089018a55988c52998b209551600288029096019586559251949096018054975191519651925198511515600160f01b027fff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff998516600160c01b02999099167fff00000000000000ffffffffffffffffffffffffffffffffffffffffffffffff938516600160901b027fffffffffffffffff000000000000ffffffffffffffffffffffffffffffffffff9886166c0100000000000000000000000002989098167fffffffffffffffff000000000000000000000000ffffffffffffffffffffffff9386166601000000000000026bffffffffffffffffffffffff19909a169690951695909517979097171691909117939093179290921691909117929092179055906130d7888661359b565b6008549091506001600160a01b03166340c10f19306130f6848c614383565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e085901b1681526001600160a01b0390921660048301526024820152604401600060405180830381600087803b15801561315457600080fd5b505af1158015613168573d6000803e3d6000fd5b5050505082156132eb576040517f995846bd00000000000000000000000000000000000000000000000000000000815230600482015260248101899052600160448201526000907f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03169063995846bd9060640160408051808303816000875af1158015613201573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906132259190614446565b6040517f78f1f7780000000000000000000000000000000000000000000000000000000081526001600160a01b038d81166004830152602482018390529193507f000000000000000000000000000000000000000000000000000000000000000090911691506378f1f77890604401600060405180830381600087803b1580156132ae57600080fd5b505af11580156132c2573d6000803e3d6000fd5b505050506001600160a01b038a1660009081526007602090815260408083208684529091529020555b50979650505050505050565b604080516001600160a01b0385811660248301528481166044830152606480830185905283518084039091018152608490920183526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167f23b872dd000000000000000000000000000000000000000000000000000000001790529151600092839290881691613389919061446a565b6000604051808303816000865af19150503d80600081146133c6576040519150601f19603f3d011682016040523d82523d6000602084013e6133cb565b606091505b50915091508180156133f55750805115806133f55750808060200190518101906133f591906141ba565b6134415760405162461bcd60e51b815260206004820152601460248201527f5452414e534645525f46524f4d5f4641494c45440000000000000000000000006044820152606401610727565b505050505050565b60008160ff168360ff161015613482576134638383614486565b6134719060ff16600a6144a9565b61347b90856144b5565b90506134b5565b8160ff168360ff1611156134b25761349a8284614486565b6134a89060ff16600a6144a9565b61347b90856143e3565b50825b9392505050565b600030338360096040516020016134d694939291906145a6565b604051602081830303815290604052805190602001209050919050565b60006134b582613502856137bb565b906137f6565b60008060009054906101000a90046001600160a01b03166001600160a01b031663ef81b4d46040518163ffffffff1660e01b8152600401602060405180830381865afa15801561355c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906135809190614065565b6001600160a01b0316826001600160a01b0316149050919050565b600080612710600154856135af91906142ca565b6135b991906142ff565b90506000612710600254866135ce91906142ca565b6135d891906142ff565b6001600160a01b03851660009081526004602052604090205490915060ff16156136e0576001600160a01b03841660009081526003602052604081208054839290613624908490614383565b9250508190555081600360008060009054906101000a90046001600160a01b03166001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015613682573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906136a69190614065565b6001600160a01b03166001600160a01b0316815260200190815260200160002060008282546136d59190614383565b909155506137a89050565b6136ea8183614383565b60008054604080517f452a93200000000000000000000000000000000000000000000000000000000081529051600393926001600160a01b03169163452a93209160048083019260209291908290030181865afa15801561374f573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906137739190614065565b6001600160a01b03166001600160a01b0316815260200190815260200160002060008282546137a29190614383565b90915550505b6137b28183614383565b95945050505050565b6040517f19457468657265756d205369676e6564204d6573736167653a0a3332000000006020820152603c8101829052600090605c016134d6565b60008060006138058585613812565b91509150610a2281613882565b6000808251604114156138495760208301516040840151606085015160001a61383d87828585613a76565b9450945050505061387b565b8251604014156138735760208301516040840151613868868383613b63565b93509350505061387b565b506000905060025b9250929050565b600081600481111561389657613896614688565b141561389f5750565b60018160048111156138b3576138b3614688565b14156139015760405162461bcd60e51b815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610727565b600281600481111561391557613915614688565b14156139635760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610727565b600381600481111561397757613977614688565b14156139eb5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610727565b60048160048111156139ff576139ff614688565b1415613a735760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610727565b50565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a0831115613aad5750600090506003613b5a565b8460ff16601b14158015613ac557508460ff16601c14155b15613ad65750600090506004613b5a565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015613b2a573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b038116613b5357600060019250925050613b5a565b9150600090505b94509492505050565b6000807f7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff831681613b9960ff86901c601b614383565b9050613ba787828885613a76565b935093505050935093915050565b828054613bc190614571565b90600052602060002090601f016020900481019282613be35760008555613c29565b82601f10613bfc5782800160ff19823516178555613c29565b82800160010185558215613c29579182015b82811115613c29578235825591602001919060010190613c0e565b50613c35929150613c39565b5090565b5b80821115613c355760008155600101613c3a565b6001600160a01b0381168114613a7357600080fd5b600060208284031215613c7557600080fd5b81356134b581613c4e565b600060208284031215613c9257600080fd5b5035919050565b6020808252825182820181905260009190848201906040850190845b81811015613cd157835183529284019291840191600101613cb5565b50909695505050505050565b60008060408385031215613cf057600080fd5b50508035926020909101359150565b60008083601f840112613d1157600080fd5b50813567ffffffffffffffff811115613d2957600080fd5b60208301915083602082850101111561387b57600080fd5b60008060208385031215613d5457600080fd5b823567ffffffffffffffff811115613d6b57600080fd5b613d7785828601613cff565b90969095509350505050565b600080600080600080600060c0888a031215613d9e57600080fd5b8735965060208801359550604088013594506060880135613dbe81613c4e565b93506080880135613dce81613c4e565b925060a088013567ffffffffffffffff811115613dea57600080fd5b613df68a828b01613cff565b989b979a50959850939692959293505050565b634e487b7160e01b600052604160045260246000fd5b6040805190810167ffffffffffffffff81118282101715613e4257613e42613e09565b60405290565b604051601f8201601f1916810167ffffffffffffffff81118282101715613e7157613e71613e09565b604052919050565b600082601f830112613e8a57600080fd5b613e92613e1f565b806040840185811115613ea457600080fd5b845b81811015610c59578035845260209384019301613ea6565b8015158114613a7357600080fd5b60008060008060006101008688031215613ee557600080fd5b8535613ef081613c4e565b9450602086810135613f0181613c4e565b9450613f108860408901613e79565b935087609f880112613f2157600080fd5b613f29613e1f565b8060c089018a811115613f3b57600080fd5b60808a015b81811015613f60578035613f5381613ebe565b8452928401928401613f40565b50819550613f6e8b82613e79565b9450505050509295509295909350565b60008060408385031215613f9157600080fd5b8235613f9c81613c4e565b946020939093013593505050565b60008060408385031215613fbd57600080fd5b8235613fc881613c4e565b915060208381013567ffffffffffffffff80821115613fe657600080fd5b818601915086601f830112613ffa57600080fd5b81358181111561400c5761400c613e09565b8060051b915061401d848301613e48565b818152918301840191848101908984111561403757600080fd5b938501935b838510156140555784358252938501939085019061403c565b8096505050505050509250929050565b60006020828403121561407757600080fd5b81516134b581613c4e565b60005b8381101561409d578181015183820152602001614085565b83811115612f3d5750506000910152565b60208152600082518060208401526140cd816040850160208701614082565b601f01601f19169190910160400192915050565b634e487b7160e01b600052603260045260246000fd5b805169ffffffffffffffffffff8116811461411157600080fd5b919050565b600080600080600060a0868803121561412e57600080fd5b614137866140f7565b945060208601519350604086015192506060860151915061415a608087016140f7565b90509295509295909350565b60006020828403121561417857600080fd5b815160ff811681146134b557600080fd5b634e487b7160e01b600052601160045260246000fd5b60006000198214156141b3576141b3614189565b5060010190565b6000602082840312156141cc57600080fd5b81516134b581613ebe565b600181815b808511156142125781600019048211156141f8576141f8614189565b8085161561420557918102915b93841c93908002906141dc565b509250929050565b60008261422957506001610919565b8161423657506000610919565b816001811461424c576002811461425657614272565b6001915050610919565b60ff84111561426757614267614189565b50506001821b610919565b5060208310610133831016604e8410600b8410161715614295575081810a610919565b61429f83836141d7565b80600019048211156142b3576142b3614189565b029392505050565b60006134b560ff84168361421a565b60008160001904831182151516156142e4576142e4614189565b500290565b634e487b7160e01b600052601260045260246000fd5b60008261430e5761430e6142e9565b500490565b60208152816020820152818360408301376000818301604090810191909152601f909201601f19160101919050565b60008282101561435457614354614189565b500390565b600065ffffffffffff80831681851680830382111561437a5761437a614189565b01949350505050565b6000821982111561439657614396614189565b500190565b600067ffffffffffffffff80831681851680830382111561437a5761437a614189565b600060ff821660ff84168060ff038211156143db576143db614189565b019392505050565b6000826143f2576143f26142e9565b60001983147f80000000000000000000000000000000000000000000000000000000000000008314161561442857614428614189565b500590565b60006020828403121561443f57600080fd5b5051919050565b6000806040838503121561445957600080fd5b505080516020909101519092909150565b6000825161447c818460208701614082565b9190910192915050565b600060ff821660ff8416808210156144a0576144a0614189565b90039392505050565b60006134b5838361421a565b60007f7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6000841360008413858304851182821616156144f6576144f6614189565b7f8000000000000000000000000000000000000000000000000000000000000000600087128682058812818416161561453157614531614189565b6000871292508782058712848416161561454d5761454d614189565b8785058712818416161561456357614563614189565b505050929093029392505050565b600181811c9082168061458557607f821691505b60208210811415612e9657634e487b7160e01b600052602260045260246000fd5b60006bffffffffffffffffffffffff19808760601b168352808660601b166014840152506028845160206145df82848701838a01614082565b855491850191600090600181811c90808316806145fd57607f831692505b85831081141561461b57634e487b7160e01b85526022600452602485fd5b80801561462f576001811461464457614675565b60ff1985168989015288848901019550614675565b60008c81526020902060005b8581101561466b5781548a82018c0152908401908801614650565b5050888489010195505b50939d9c50505050505050505050505050565b634e487b7160e01b600052602160045260246000fdfea264697066735822122086445cea095181ab1f5b7ed16b01d3b0707fa19ef1a6263600e497e7c658003564736f6c634300080a0033000000000000000000000000fe9fab692c951eeb28345b3a22008f4057eaa232000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac2000000000000000000000000e249e013e7aabcc79726e9d62b0c2d89cdd69f5100000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff4000000000000000000000000f3143ae15dea73f4e8f32360f6b669173c854388
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106102415760003560e01c8063ae10426511610145578063d2390aa2116100bd578063e3684e391161008c578063e4994e9611610071578063e4994e9614610637578063ec2c90161461064a578063f3191a461461065257600080fd5b8063e3684e39146105ff578063e481b2651461062457600080fd5b8063d2390aa21461055d578063d6db4df814610570578063d936547e14610583578063e0b117ff146105a657600080fd5b8063bf7e214f11610114578063c0aa0e8a116100f9578063c0aa0e8a146104cc578063c3e0fb1c14610505578063c9b67af51461055557600080fd5b8063bf7e214f1461048e578063c0680e20146104b957600080fd5b8063ae104265146103e1578063b1283e77146103f4578063b6d8eee014610452578063be399be51461047b57600080fd5b8063654e51e7116101d8578063964561c4116101a75780639b19251a1161018c5780639b19251a146103b35780639c769787146103c6578063a4220610146103ce57600080fd5b8063964561c41461036b5780639a1e46d5146103a057600080fd5b8063654e51e71461031f5780636a6c575d146103325780637a9e5e4b146103455780637ed6c9261461035857600080fd5b8063275074581161021457806327507458146102c1578063333d7d77146102e45780633d18b91214610304578063649144391461030c57600080fd5b80630700037d146102465780630aebeb4e1461027957806316345f181461028e5780631885f580146102b8575b600080fd5b610266610254366004613c63565b60036020526000908152604090205481565b6040519081526020015b60405180910390f35b61028c610287366004613c80565b61065b565b005b6102a161029c366004613c63565b6107c7565b6040805192835260ff909116602083015201610270565b61026660015481565b6102d46102cf366004613c80565b6108b2565b6040519015158152602001610270565b6102f76102f2366004613c63565b61091f565b6040516102709190613c99565b61028c610a2a565b6102f761031a366004613c63565b610ad5565b61028c61032d366004613cdd565b610c64565b610266610340366004613cdd565b610d79565b61028c610353366004613c63565b610df0565b61028c610366366004613d41565b610f12565b61037e610379366004613d83565b61101d565b6040805182518152602080840151908201529181015190820152606001610270565b6102666103ae366004613ecc565b611401565b61028c6103c1366004613c63565b6118a5565b61028c61199b565b6102666103dc366004613f7e565b611c6c565b6102666103ef366004613c80565b61215d565b610407610402366004613c80565b6121f4565b604080519788526001600160a01b0396871660208901529490951693860193909352901515606085015267ffffffffffffffff16608084015260a083015260c082015260e001610270565b610266610460366004613c63565b6001600160a01b031660009081526005602052604090205490565b610266610489366004613c63565b612272565b6000546104a1906001600160a01b031681565b6040516001600160a01b039091168152602001610270565b6102666104c7366004613f7e565b612281565b6104df6104da366004613c80565b6122b2565b60408051931515845265ffffffffffff9283166020850152911690820152606001610270565b610518610513366004613f7e565b6122f2565b6040805196875265ffffffffffff9586166020880152938516938601939093529083166060850152151560808401521660a082015260c001610270565b6102f761243b565b61026661056b366004613faa565b612524565b61028c61057e366004613f7e565b6128bb565b6102d4610591366004613c63565b60046020526000908152604090205460ff1681565b6105b96105b4366004613f7e565b6129c0565b6040805197885265ffffffffffff96871660208901529486169487019490945291841660608601528316608085015290911660a0830152151560c082015260e001610270565b61061261060d366004613c80565b612a45565b60405160ff9091168152602001610270565b6102f7610632366004613c63565b612a69565b61028c610645366004613c63565b612cba565b6102f7612e0c565b61026660025481565b60008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa1580156106ac573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906106d09190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906107305760405162461bcd60e51b815260040161072791906140ae565b60405180910390fd5b5042600b8281548110610745576107456140e1565b9060005260206000200160000160076101000a81548165ffffffffffff021916908365ffffffffffff1602179055506000600a8281548110610789576107896140e1565b6000918252602082206005909102019190915560405182917f8401d05adbea6548a6999cc1540766e6d2ff919292142862893d0e62ec79fbe591a250565b6000806000806000806000876001600160a01b031663feaf968c6040518163ffffffff1660e01b815260040160a060405180830381865afa158015610810573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108349190614116565b945094509450945094506000886001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa15801561087e573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906108a29190614166565b9499949850939650505050505050565b6000600a82815481106108c7576108c76140e1565b906000526020600020906005020160000154600014158015610919575042600b83815481106108f8576108f86140e1565b600091825260209091200154670100000000000000900465ffffffffffff16115b92915050565b6001600160a01b0381166000908152600e6020908152604080832080548251818502810185019093528083526060949383018282801561097e57602002820191906000526020600020905b81548152602001906001019080831161096a575b505050505090506000815167ffffffffffffffff8111156109a1576109a1613e09565b6040519080825280602002602001820160405280156109ca578160200160208202803683370190505b50905060005b8251811015610a22578281815181106109eb576109eb6140e1565b6020026020010151828281518110610a0557610a056140e1565b602090810291909101015280610a1a8161419f565b9150506109d0565b509392505050565b3360008181526003602052604080822080549290555163a9059cbb60e01b8152600481019290925260248201819052906001600160a01b037f000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac2169063a9059cbb906044016020604051808303816000875af1158015610aad573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610ad191906141ba565b5050565b6001600160a01b0381166000908152600e60209081526040808320805482518185028101850190935280835260609493830182828015610b3457602002820191906000526020600020905b815481526020019060010190808311610b20575b50505050509050600080600090505b8251811015610b9357610b6e838281518110610b6157610b616140e1565b60200260200101516108b2565b15610b815781610b7d8161419f565b9250505b80610b8b8161419f565b915050610b43565b5060008167ffffffffffffffff811115610baf57610baf613e09565b604051908082528060200260200182016040528015610bd8578160200160208202803683370190505b5090506000805b8451811015610c5957610bfd858281518110610b6157610b616140e1565b15610c4757848181518110610c1457610c146140e1565b6020026020010151838381518110610c2e57610c2e6140e1565b602090810291909101015281610c438161419f565b9250505b80610c518161419f565b915050610bdf565b509095945050505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610cb5573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610cd99190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610d305760405162461bcd60e51b815260040161072791906140ae565b506002829055600181905560408051838152602081018390527f41ddb6f76c2aab8405d1cca4bd752e126ac8976c1203888790f8594c7ba3661191015b60405180910390a15050565b600080600c8381548110610d8f57610d8f6140e1565b6000918252602091829020604080519384019052015460ff16808252909150610db990600a6142bb565b610dc28461215d565b610dd486670de0b6b3a76400006142ca565b610dde91906142ff565b610de891906142ff565b949350505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610e41573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610e659190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610ebc5760405162461bcd60e51b815260040161072791906140ae565b506000805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b038316908117825560405190917f2f658b440c35314f52658ea8a740e05b284cdc84dc9ae01e891f21b8933e7cad91a250565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015610f63573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610f879190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090610fde5760405162461bcd60e51b815260040161072791906140ae565b50610feb60098383613bb5565b507fc84ba0d041142642d7c555ad8e697a8d84a7bc3fdf46d377be42ef3ad71b5eda8282604051610d6d929190614313565b61104160405180606001604052806000815260200160008152602001600081525090565b600d546001600160a01b0316331461106d5761106d604051806020016040528060008152508484612e9c565b6000600a8981548110611082576110826140e1565b906000526020600020906005020190506000600b8a815481106110a7576110a76140e1565b600091825260209182902060408051606081018252919092015460ff81161515825265ffffffffffff610100820481169483019490945267010000000000000090048316918101829052925042918216106111445760405162461bcd60e51b815260206004820152601c60248201527f4465706f7369746f72793a206d61726b657420636f6e636c75646564000000006044820152606401610727565b600061114f8c61215d565b9050898111156111a15760405162461bcd60e51b815260206004820152601f60248201527f4465706f7369746f72793a206d6f7265207468616e206d6178207072696365006044820152606401610727565b600c8c815481106111b4576111b46140e1565b6000918252602090912001546111ce9060ff16600a6142bb565b816111e18d670de0b6b3a76400006142ca565b6111eb91906142ff565b6111f591906142ff565b85526002840154600160a01b900460ff16611211578451611213565b8a5b845410156112635760405162461bcd60e51b815260206004820152601d60248201527f4465706f7369746f72793a2063617061636974792065786365656465640000006044820152606401610727565b6002840154600160a01b900460ff1661127d57845161127f565b8a5b8460000160008282546112929190614342565b909155505083546112c9576040518c907f8401d05adbea6548a6999cc1540766e6d2ff919292142862893d0e62ec79fbe590600090a25b82516112d95782602001516112e9565b8183602001516112e99190614359565b65ffffffffffff1660208601526003840180548c919060009061130d908490614383565b9091555050845160028501805460159061134b9084907501000000000000000000000000000000000000000000900467ffffffffffffffff1661439b565b92506101000a81548167ffffffffffffffff021916908367ffffffffffffffff1602179055508b7f7880508a48fd3aee88f7e15917d85e39c3ad059e51ad4aca9bb46e7b4938b9618c836040516113ac929190918252602082015260400190565b60405180910390a26113cc89866000015187602001518f8c600080612f43565b604086015260085460018501546113f2916001600160a01b03918216913391168e6132f7565b50505050979650505050505050565b60008060009054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa158015611455573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906114799190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906114d05760405162461bcd60e51b815260040161072791906140ae565b506000866001600160a01b031663313ce5676040518163ffffffff1660e01b8152600401602060405180830381865afa158015611511573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906115359190614166565b60ff169050600a805490509150600a6040518060e0016040528087600060028110611562576115626140e1565b60200201518152602001896001600160a01b03168152602001886001600160a01b031681526020018660006002811061159d5761159d6140e1565b602002015115158152602001600067ffffffffffffffff16815260200160008152602001876001600281106115d4576115d46140e1565b60209081029190910151909152825460018082018555600094855282852084516005909302019182558383015182820180546001600160a01b0392831673ffffffffffffffffffffffffffffffffffffffff199091161790556040808601516002850180546060808a015160808b015167ffffffffffffffff167501000000000000000000000000000000000000000000027fffffff0000000000000000ffffffffffffffffffffffffffffffffffffffffff911515600160a01b027fffffffffffffffffffffff00000000000000000000000000000000000000000090941695881695909517929092179190911692909217905560a0870151600386015560c090960151600490940193909355825194850183528984015115158552885165ffffffffffff9081168686019081528a8601518216878601908152600b80548087018255908a5297517f0175b7a638427703f0dbe7bb9bbf987a2551717b34e79f33b5b1008d1fa01db99098018054925191517fffffffffffffffffffffffffffffffffffffffffffffffffff000000000000009093169815157fffffffffffffffffffffffffffffffffffffffffffffffffff000000000000ff169890981761010091841691909102177fffffffffffffffffffffffffffffffffffffff000000000000ffffffffffffff166701000000000000009190921602179094558151808401835260ff8781168252600c8054808501825590885291517fdf6966c971051c3d54ec59162606531493a51404a002842f56009d7e5cf4a8c7909201805460ff1916929091169190911790558b8416808652600e8452828620805492830181558652948390200186905588820151815190815290517f000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac29093169286927f2f6ff727bd580b1d1b8332e28aa93ed4ec9d8b08d6e30d6b4c9f7aa63ca17f63928290030190a45095945050505050565b60008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa1580156118f6573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061191a9190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b815250906119715760405162461bcd60e51b815260040161072791906140ae565b506001600160a01b03166000908152600460205260409020805460ff19811660ff90911615179055565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa1580156119ec573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a109190614065565b6001600160a01b0316336001600160a01b03161480611ab4575060008054906101000a90046001600160a01b03166001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015611a7b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611a9f9190614065565b6001600160a01b0316336001600160a01b0316145b80611b44575060008054906101000a90046001600160a01b03166001600160a01b0316630505c8c96040518163ffffffff1660e01b8152600401602060405180830381865afa158015611b0b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b2f9190614065565b6001600160a01b0316336001600160a01b0316145b611b905760405162461bcd60e51b815260206004820152600f60248201527f4f6e6c7920617574686f72697a656400000000000000000000000000000000006044820152606401610727565b60008060009054906101000a90046001600160a01b03166001600160a01b031663fbfa77cf6040518163ffffffff1660e01b8152600401602060405180830381865afa158015611be4573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611c089190614065565b6008805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0383169081179091556040519081529091507f7dae230f18360d76a040c81f050aa14eb9d6dc7901b20fc5d855e2a20fe814d19060200160405180910390a150565b6001600160a01b0382811660009081526006602090815260408083208584529091528120549091163314611ce25760405162461bcd60e51b815260206004820152601e60248201527f4465706f7369746f72793a207472616e73666572206e6f7420666f756e6400006044820152606401610727565b6001600160a01b0383166000908152600560205260409020805483908110611d0c57611d0c6140e1565b60009182526020909120600290910201600101546c01000000000000000000000000900465ffffffffffff1615611d855760405162461bcd60e51b815260206004820152601960248201527f4465706f7369746f72793a206e6f74652072656465656d6564000000000000006044820152606401610727565b5033600090815260056020526040808220546001600160a01b03851683529120805483908110611db757611db76140e1565b9060005260206000209060020201600101601e9054906101000a900460ff1615611ead576001600160a01b038381166000908152600760208181526040808420878552825280842054338086529383528185208786529092529283902081905591517f78f1f77800000000000000000000000000000000000000000000000000000000815260048101919091526024810182905290917f00000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff416906378f1f77890604401600060405180830381600087803b158015611e9357600080fd5b505af1158015611ea7573d6000803e3d6000fd5b50505050505b336000908152600560205260408082206001600160a01b03861683529120805484908110611edd57611edd6140e1565b60009182526020808320845460018181018755958552828520600294850290920180549190940290910190815591840180549290940180547fffffffffffffffffffffffffffffffffffffffffffffffffffff000000000000811665ffffffffffff948516908117835586546601000000000000908190048616026bffffffffffffffffffffffff19909216171780825585546c01000000000000000000000000908190048516027fffffffffffffffffffffffffffff000000000000ffffffffffffffffffffffff8216811783558654600160901b908190048616027fffffffffffffffff000000000000ffffffffffffffffffffffffffffffffffff9091167fffffffffffffffff000000000000000000000000ffffffffffffffffffffffff90921691909117178082558554600160c01b908190049094169093027fffff000000000000ffffffffffffffffffffffffffffffffffffffffffffffff841681178255945460ff600160f01b91829004161515027fff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff9095167fff00000000000000ffffffffffffffffffffffffffffffffffffffffffffffff909316929092179390931790556001600160a01b03851681526005909152604090208054839081106120cc576120cc6140e1565b60009182526020808320600292909202909101918255600190910180547fff00000000000000000000000000000000000000000000000000000000000000169055604080516001600160a01b0386168152339281019290925281018390527fac662197bb43cbfbf62b5caf539eb823ba3ee6f13941f9978304958a2c916ebf9060600160405180910390a192915050565b600080600061219a600a8581548110612178576121786140e1565b60009182526020909120600260059092020101546001600160a01b03166107c7565b9150915060006121dc600a86815481106121b6576121b66140e1565b90600052602060002090600502016004015460098460096121d791906143be565b613449565b905060006121ea84836143e3565b9695505050505050565b600a818154811061220457600080fd5b6000918252602090912060059091020180546001820154600283015460038401546004909401549294506001600160a01b039182169391811692600160a01b820460ff1692750100000000000000000000000000000000000000000090920467ffffffffffffffff16919087565b60006109198261056b84612a69565b600e602052816000526040600020818154811061229d57600080fd5b90600052602060002001600091509150505481565b600b81815481106122c257600080fd5b60009182526020909120015460ff8116915065ffffffffffff610100820481169167010000000000000090041683565b6000806000806000806000600560008a6001600160a01b03166001600160a01b031681526020019081526020016000208881548110612333576123336140e1565b60009182526020918290206040805160e0810182526002909302909101805480845260019091015465ffffffffffff8082169585018690526601000000000000820481169385018490526c01000000000000000000000000820481166060860152600160901b820481166080860152600160c01b82041660a085015260ff600160f01b90910416151560c0840152995091975090955090504285116123d95760006123f1565b42816040015165ffffffffffff166123f19190614342565b9350806060015165ffffffffffff16600014801561241b575042816040015165ffffffffffff1611155b80156124275750805115155b92508060a001519150509295509295509295565b60606000805b600a5481101561247957612454816108b2565b1561246757816124638161419f565b9250505b806124718161419f565b915050612441565b5060008167ffffffffffffffff81111561249557612495613e09565b6040519080825280602002602001820160405280156124be578160200160208202803683370190505b5090506000805b600a5481101561251b576124d8816108b2565b1561250957808383815181106124f0576124f06140e1565b6020908102919091010152816125058161419f565b9250505b806125138161419f565b9150506124c5565b50909392505050565b6000428180805b855181101561277b5760008061255a8989858151811061254d5761254d6140e1565b60200260200101516122f2565b50945050505091508015612766576001600160a01b038916600090815260056020526040902088518791908a9086908110612597576125976140e1565b6020026020010151815481106125af576125af6140e1565b9060005260206000209060020201600101600c6101000a81548165ffffffffffff021916908365ffffffffffff16021790555081876125ee9190614383565b6001600160a01b038a16600090815260056020526040902089519198509089908590811061261e5761261e6140e1565b602002602001015181548110612636576126366140e1565b9060005260206000209060020201600101601e9054906101000a900460ff1615612759576001600160a01b0389166000908152600760205260408120895182908b9087908110612688576126886140e1565b602002602001015181526020019081526020016000205490507f00000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff46001600160a01b031663b3e504098b836040518363ffffffff1660e01b81526004016127039291906001600160a01b03929092168252602082015260400190565b6020604051808303816000875af1158015612722573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612746919061442d565b506127518387614383565b955050612766565b6127638285614383565b93505b505080806127739061419f565b91505061252b565b5080156128175760405163a9059cbb60e01b81526001600160a01b038781166004830152602482018390527f000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac2169063a9059cbb906044016020604051808303816000875af11580156127f1573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061281591906141ba565b505b81156128b25760405163a9059cbb60e01b81526001600160a01b038781166004830152602482018490527f000000000000000000000000e249e013e7aabcc79726e9d62b0c2d89cdd69f51169063a9059cbb906044016020604051808303816000875af115801561288c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906128b091906141ba565b505b50505092915050565b3360009081526005602052604090208054829081106128dc576128dc6140e1565b600091825260209091206001600290920201015465ffffffffffff166129445760405162461bcd60e51b815260206004820152601a60248201527f4465706f7369746f72793a206e6f7465206e6f7420666f756e640000000000006044820152606401610727565b336000818152600660209081526040808320858452825291829020805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b03871690811790915582519384529083015281018290527f46a855c725ecb3b899b429c361a8e87ced35203a422c4324e83b6a43b0b70c2390606001610d6d565b600560205281600052604060002081815481106129dc57600080fd5b60009182526020909120600290910201805460019091015490925065ffffffffffff8082169250660100000000000082048116916c010000000000000000000000008104821691600160901b8204811691600160c01b810490911690600160f01b900460ff1687565b600c8181548110612a5557600080fd5b60009182526020909120015460ff16905081565b6001600160a01b0381166000908152600560209081526040808320805482518185028101850190935280835260609493849084015b82821015612b405760008481526020908190206040805160e081018252600286029092018054835260019081015465ffffffffffff80821685870152660100000000000082048116938501939093526c01000000000000000000000000810483166060850152600160901b810483166080850152600160c01b810490921660a0840152600160f01b90910460ff16151560c08301529083529092019101612a9e565b505050509050600080600090505b8251811015612bcf57828181518110612b6957612b696140e1565b60200260200101516060015165ffffffffffff166000148015612baa5750828181518110612b9957612b996140e1565b602002602001015160000151600014155b15612bbd5781612bb98161419f565b9250505b80612bc78161419f565b915050612b4e565b5060008167ffffffffffffffff811115612beb57612beb613e09565b604051908082528060200260200182016040528015612c14578160200160208202803683370190505b5090506000805b8451811015610c5957848181518110612c3657612c366140e1565b60200260200101516060015165ffffffffffff166000148015612c775750848181518110612c6657612c666140e1565b602002602001015160000151600014155b15612ca85780838381518110612c8f57612c8f6140e1565b602090810291909101015281612ca48161419f565b9250505b80612cb28161419f565b915050612c1b565b60008054906101000a90046001600160a01b03166001600160a01b0316630c340a246040518163ffffffff1660e01b8152600401602060405180830381865afa158015612d0b573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612d2f9190614065565b6001600160a01b0316336001600160a01b0316146040518060400160405280600c81526020016b15539055551213d49256915160a21b81525090612d865760405162461bcd60e51b815260040161072791906140ae565b506001600160a01b038116612ddd5760405162461bcd60e51b815260206004820152600c60248201527f5a65726f206164647265737300000000000000000000000000000000000000006044820152606401610727565b600d805473ffffffffffffffffffffffffffffffffffffffff19166001600160a01b0392909216919091179055565b600a5460609060009067ffffffffffffffff811115612e2d57612e2d613e09565b604051908082528060200260200182016040528015612e56578160200160208202803683370190505b50905060005b600a54811015612e965780828281518110612e7957612e796140e1565b602090810291909101015280612e8e8161419f565b915050612e5c565b50919050565b6000612ee6612eaa856134bc565b84848080601f0160208091040260200160405190810160405280939291908181526020018383808284376000920191909152506134f392505050565b9050612ef181613508565b612f3d5760405162461bcd60e51b815260206004820152601d60248201527f5369676e617475726520766572696669636174696f6e206661696c65640000006044820152606401610727565b50505050565b6001600160a01b03871660009081526005602090815260408083208054825160e0810184528b815265ffffffffffff4281168287019081528c8216958301958652606083018881528c8316608085019081528b841660a086019081528b151560c0870190815260018089018a55988c52998b209551600288029096019586559251949096018054975191519651925198511515600160f01b027fff00ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff998516600160c01b02999099167fff00000000000000ffffffffffffffffffffffffffffffffffffffffffffffff938516600160901b027fffffffffffffffff000000000000ffffffffffffffffffffffffffffffffffff9886166c0100000000000000000000000002989098167fffffffffffffffff000000000000000000000000ffffffffffffffffffffffff9386166601000000000000026bffffffffffffffffffffffff19909a169690951695909517979097171691909117939093179290921691909117929092179055906130d7888661359b565b6008549091506001600160a01b03166340c10f19306130f6848c614383565b6040517fffffffff0000000000000000000000000000000000000000000000000000000060e085901b1681526001600160a01b0390921660048301526024820152604401600060405180830381600087803b15801561315457600080fd5b505af1158015613168573d6000803e3d6000fd5b5050505082156132eb576040517f995846bd00000000000000000000000000000000000000000000000000000000815230600482015260248101899052600160448201526000907f00000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff46001600160a01b03169063995846bd9060640160408051808303816000875af1158015613201573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906132259190614446565b6040517f78f1f7780000000000000000000000000000000000000000000000000000000081526001600160a01b038d81166004830152602482018390529193507f00000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff490911691506378f1f77890604401600060405180830381600087803b1580156132ae57600080fd5b505af11580156132c2573d6000803e3d6000fd5b505050506001600160a01b038a1660009081526007602090815260408083208684529091529020555b50979650505050505050565b604080516001600160a01b0385811660248301528481166044830152606480830185905283518084039091018152608490920183526020820180517bffffffffffffffffffffffffffffffffffffffffffffffffffffffff167f23b872dd000000000000000000000000000000000000000000000000000000001790529151600092839290881691613389919061446a565b6000604051808303816000865af19150503d80600081146133c6576040519150601f19603f3d011682016040523d82523d6000602084013e6133cb565b606091505b50915091508180156133f55750805115806133f55750808060200190518101906133f591906141ba565b6134415760405162461bcd60e51b815260206004820152601460248201527f5452414e534645525f46524f4d5f4641494c45440000000000000000000000006044820152606401610727565b505050505050565b60008160ff168360ff161015613482576134638383614486565b6134719060ff16600a6144a9565b61347b90856144b5565b90506134b5565b8160ff168360ff1611156134b25761349a8284614486565b6134a89060ff16600a6144a9565b61347b90856143e3565b50825b9392505050565b600030338360096040516020016134d694939291906145a6565b604051602081830303815290604052805190602001209050919050565b60006134b582613502856137bb565b906137f6565b60008060009054906101000a90046001600160a01b03166001600160a01b031663ef81b4d46040518163ffffffff1660e01b8152600401602060405180830381865afa15801561355c573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906135809190614065565b6001600160a01b0316826001600160a01b0316149050919050565b600080612710600154856135af91906142ca565b6135b991906142ff565b90506000612710600254866135ce91906142ca565b6135d891906142ff565b6001600160a01b03851660009081526004602052604090205490915060ff16156136e0576001600160a01b03841660009081526003602052604081208054839290613624908490614383565b9250508190555081600360008060009054906101000a90046001600160a01b03166001600160a01b031663452a93206040518163ffffffff1660e01b8152600401602060405180830381865afa158015613682573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906136a69190614065565b6001600160a01b03166001600160a01b0316815260200190815260200160002060008282546136d59190614383565b909155506137a89050565b6136ea8183614383565b60008054604080517f452a93200000000000000000000000000000000000000000000000000000000081529051600393926001600160a01b03169163452a93209160048083019260209291908290030181865afa15801561374f573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906137739190614065565b6001600160a01b03166001600160a01b0316815260200190815260200160002060008282546137a29190614383565b90915550505b6137b28183614383565b95945050505050565b6040517f19457468657265756d205369676e6564204d6573736167653a0a3332000000006020820152603c8101829052600090605c016134d6565b60008060006138058585613812565b91509150610a2281613882565b6000808251604114156138495760208301516040840151606085015160001a61383d87828585613a76565b9450945050505061387b565b8251604014156138735760208301516040840151613868868383613b63565b93509350505061387b565b506000905060025b9250929050565b600081600481111561389657613896614688565b141561389f5750565b60018160048111156138b3576138b3614688565b14156139015760405162461bcd60e51b815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610727565b600281600481111561391557613915614688565b14156139635760405162461bcd60e51b815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610727565b600381600481111561397757613977614688565b14156139eb5760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610727565b60048160048111156139ff576139ff614688565b1415613a735760405162461bcd60e51b815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202776272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610727565b50565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a0831115613aad5750600090506003613b5a565b8460ff16601b14158015613ac557508460ff16601c14155b15613ad65750600090506004613b5a565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015613b2a573d6000803e3d6000fd5b5050604051601f1901519150506001600160a01b038116613b5357600060019250925050613b5a565b9150600090505b94509492505050565b6000807f7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff831681613b9960ff86901c601b614383565b9050613ba787828885613a76565b935093505050935093915050565b828054613bc190614571565b90600052602060002090601f016020900481019282613be35760008555613c29565b82601f10613bfc5782800160ff19823516178555613c29565b82800160010185558215613c29579182015b82811115613c29578235825591602001919060010190613c0e565b50613c35929150613c39565b5090565b5b80821115613c355760008155600101613c3a565b6001600160a01b0381168114613a7357600080fd5b600060208284031215613c7557600080fd5b81356134b581613c4e565b600060208284031215613c9257600080fd5b5035919050565b6020808252825182820181905260009190848201906040850190845b81811015613cd157835183529284019291840191600101613cb5565b50909695505050505050565b60008060408385031215613cf057600080fd5b50508035926020909101359150565b60008083601f840112613d1157600080fd5b50813567ffffffffffffffff811115613d2957600080fd5b60208301915083602082850101111561387b57600080fd5b60008060208385031215613d5457600080fd5b823567ffffffffffffffff811115613d6b57600080fd5b613d7785828601613cff565b90969095509350505050565b600080600080600080600060c0888a031215613d9e57600080fd5b8735965060208801359550604088013594506060880135613dbe81613c4e565b93506080880135613dce81613c4e565b925060a088013567ffffffffffffffff811115613dea57600080fd5b613df68a828b01613cff565b989b979a50959850939692959293505050565b634e487b7160e01b600052604160045260246000fd5b6040805190810167ffffffffffffffff81118282101715613e4257613e42613e09565b60405290565b604051601f8201601f1916810167ffffffffffffffff81118282101715613e7157613e71613e09565b604052919050565b600082601f830112613e8a57600080fd5b613e92613e1f565b806040840185811115613ea457600080fd5b845b81811015610c59578035845260209384019301613ea6565b8015158114613a7357600080fd5b60008060008060006101008688031215613ee557600080fd5b8535613ef081613c4e565b9450602086810135613f0181613c4e565b9450613f108860408901613e79565b935087609f880112613f2157600080fd5b613f29613e1f565b8060c089018a811115613f3b57600080fd5b60808a015b81811015613f60578035613f5381613ebe565b8452928401928401613f40565b50819550613f6e8b82613e79565b9450505050509295509295909350565b60008060408385031215613f9157600080fd5b8235613f9c81613c4e565b946020939093013593505050565b60008060408385031215613fbd57600080fd5b8235613fc881613c4e565b915060208381013567ffffffffffffffff80821115613fe657600080fd5b818601915086601f830112613ffa57600080fd5b81358181111561400c5761400c613e09565b8060051b915061401d848301613e48565b818152918301840191848101908984111561403757600080fd5b938501935b838510156140555784358252938501939085019061403c565b8096505050505050509250929050565b60006020828403121561407757600080fd5b81516134b581613c4e565b60005b8381101561409d578181015183820152602001614085565b83811115612f3d5750506000910152565b60208152600082518060208401526140cd816040850160208701614082565b601f01601f19169190910160400192915050565b634e487b7160e01b600052603260045260246000fd5b805169ffffffffffffffffffff8116811461411157600080fd5b919050565b600080600080600060a0868803121561412e57600080fd5b614137866140f7565b945060208601519350604086015192506060860151915061415a608087016140f7565b90509295509295909350565b60006020828403121561417857600080fd5b815160ff811681146134b557600080fd5b634e487b7160e01b600052601160045260246000fd5b60006000198214156141b3576141b3614189565b5060010190565b6000602082840312156141cc57600080fd5b81516134b581613ebe565b600181815b808511156142125781600019048211156141f8576141f8614189565b8085161561420557918102915b93841c93908002906141dc565b509250929050565b60008261422957506001610919565b8161423657506000610919565b816001811461424c576002811461425657614272565b6001915050610919565b60ff84111561426757614267614189565b50506001821b610919565b5060208310610133831016604e8410600b8410161715614295575081810a610919565b61429f83836141d7565b80600019048211156142b3576142b3614189565b029392505050565b60006134b560ff84168361421a565b60008160001904831182151516156142e4576142e4614189565b500290565b634e487b7160e01b600052601260045260246000fd5b60008261430e5761430e6142e9565b500490565b60208152816020820152818360408301376000818301604090810191909152601f909201601f19160101919050565b60008282101561435457614354614189565b500390565b600065ffffffffffff80831681851680830382111561437a5761437a614189565b01949350505050565b6000821982111561439657614396614189565b500190565b600067ffffffffffffffff80831681851680830382111561437a5761437a614189565b600060ff821660ff84168060ff038211156143db576143db614189565b019392505050565b6000826143f2576143f26142e9565b60001983147f80000000000000000000000000000000000000000000000000000000000000008314161561442857614428614189565b500590565b60006020828403121561443f57600080fd5b5051919050565b6000806040838503121561445957600080fd5b505080516020909101519092909150565b6000825161447c818460208701614082565b9190910192915050565b600060ff821660ff8416808210156144a0576144a0614189565b90039392505050565b60006134b5838361421a565b60007f7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff6000841360008413858304851182821616156144f6576144f6614189565b7f8000000000000000000000000000000000000000000000000000000000000000600087128682058812818416161561453157614531614189565b6000871292508782058712848416161561454d5761454d614189565b8785058712818416161561456357614563614189565b505050929093029392505050565b600181811c9082168061458557607f821691505b60208210811415612e9657634e487b7160e01b600052602260045260246000fd5b60006bffffffffffffffffffffffff19808760601b168352808660601b166014840152506028845160206145df82848701838a01614082565b855491850191600090600181811c90808316806145fd57607f831692505b85831081141561461b57634e487b7160e01b85526022600452602485fd5b80801561462f576001811461464457614675565b60ff1985168989015288848901019550614675565b60008c81526020902060005b8581101561466b5781548a82018c0152908401908801614650565b5050888489010195505b50939d9c50505050505050505050505050565b634e487b7160e01b600052602160045260246000fdfea264697066735822122086445cea095181ab1f5b7ed16b01d3b0707fa19ef1a6263600e497e7c658003564736f6c634300080a0033
Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)
000000000000000000000000fe9fab692c951eeb28345b3a22008f4057eaa232000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac2000000000000000000000000e249e013e7aabcc79726e9d62b0c2d89cdd69f5100000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff4000000000000000000000000f3143ae15dea73f4e8f32360f6b669173c854388
-----Decoded View---------------
Arg [0] : _authority (address): 0xfe9fAb692c951eeB28345B3A22008f4057eAa232
Arg [1] : _theo (address): 0xfAc0403a24229d7e2Edd994D50F5940624CBeac2
Arg [2] : _stheo (address): 0xE249e013E7AAbCC79726e9d62B0c2d89CdD69f51
Arg [3] : _staking (address): 0x18Bba38a6F8427Ed2B65b5C6E9532CD80f93aFf4
Arg [4] : _treasury (address): 0xf3143ae15deA73F4E8F32360F6b669173c854388
-----Encoded View---------------
5 Constructor Arguments found :
Arg [0] : 000000000000000000000000fe9fab692c951eeb28345b3a22008f4057eaa232
Arg [1] : 000000000000000000000000fac0403a24229d7e2edd994d50f5940624cbeac2
Arg [2] : 000000000000000000000000e249e013e7aabcc79726e9d62b0c2d89cdd69f51
Arg [3] : 00000000000000000000000018bba38a6f8427ed2b65b5c6e9532cd80f93aff4
Arg [4] : 000000000000000000000000f3143ae15dea73f4e8f32360f6b669173c854388
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 30 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|---|---|---|---|---|
ETH | 100.00% | $0.002882 | 5,118,924.1572 | $14,755.25 |
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.