Transactions
Token Transfers
Tokens
Internal Transactions
Coin Balance History
Logs
Code
Read Contract
Write Contract
Warning! Contract bytecode has been changed and doesn't match the verified one. Therefore, interaction with this smart contract may be risky.
- Contract name:
- TimeTreasury
- Optimization enabled
- true
- Compiler version
- v0.7.5+commit.eb77ed08
- Optimization runs
- 200
- EVM Version
- default
- Verified at
- 2022-01-16T18:43:23.757013Z
Constructor Arguments
00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd000000000000000000000000ea32a96608495e54156ae48931a7c20f0dcc1a210000000000000000000000000000000000000000000000000000000000000000
Arg [0] (address) : <a href=/address/0x72c232d56542ba082592dee7c77b1c6cfa758bcd>0x72c232d56542ba082592dee7c77b1c6cfa758bcd</a>
Arg [1] (address) : <a href=/address/0xea32a96608495e54156ae48931a7c20f0dcc1a21>0xea32a96608495e54156ae48931a7c20f0dcc1a21</a>
Arg [2] (uint32) : 0
Contract source code
// SPDX-License-Identifier: AGPL-3.0-or-later pragma solidity 0.7.5; library LowGasSafeMath { /// @notice Returns x + y, reverts if sum overflows uint256 /// @param x The augend /// @param y The addend /// @return z The sum of x and y function add(uint256 x, uint256 y) internal pure returns (uint256 z) { require((z = x + y) >= x); } function add32(uint32 x, uint32 y) internal pure returns (uint32 z) { require((z = x + y) >= x); } /// @notice Returns x - y, reverts if underflows /// @param x The minuend /// @param y The subtrahend /// @return z The difference of x and y function sub(uint256 x, uint256 y) internal pure returns (uint256 z) { require((z = x - y) <= x); } function sub32(uint32 x, uint32 y) internal pure returns (uint32 z) { require((z = x - y) <= x); } /// @notice Returns x * y, reverts if overflows /// @param x The multiplicand /// @param y The multiplier /// @return z The product of x and y function mul(uint256 x, uint256 y) internal pure returns (uint256 z) { require(x == 0 || (z = x * y) / x == y); } function mul32(uint32 x, uint32 y) internal pure returns (uint32 z) { require(x == 0 || (z = x * y) / x == y); } /// @notice Returns x + y, reverts if overflows or underflows /// @param x The augend /// @param y The addend /// @return z The sum of x and y function add(int256 x, int256 y) internal pure returns (int256 z) { require((z = x + y) >= x == (y >= 0)); } /// @notice Returns x - y, reverts if overflows or underflows /// @param x The minuend /// @param y The subtrahend /// @return z The difference of x and y function sub(int256 x, int256 y) internal pure returns (int256 z) { require((z = x - y) <= x == (y >= 0)); } function div(uint256 x, uint256 y) internal pure returns(uint256 z){ require(y > 0); z=x/y; } } library Address { function isContract(address account) internal view returns (bool) { // This method relies in extcodesize, which returns 0 for contracts in // construction, since the code is only stored at the end of the // constructor execution. uint256 size; // solhint-disable-next-line no-inline-assembly assembly { size := extcodesize(account) } return size > 0; } function functionCall( address target, bytes memory data, string memory errorMessage ) internal returns (bytes memory) { return _functionCallWithValue(target, data, 0, errorMessage); } function _functionCallWithValue( address target, bytes memory data, uint256 weiValue, string memory errorMessage ) private returns (bytes memory) { require(isContract(target), "Address: call to non-contract"); // solhint-disable-next-line avoid-low-level-calls (bool success, bytes memory returndata) = target.call{ value: weiValue }(data); if (success) { return returndata; } else { if (returndata.length > 0) { // solhint-disable-next-line no-inline-assembly assembly { let returndata_size := mload(returndata) revert(add(32, returndata), returndata_size) } } else { revert(errorMessage); } } } function _verifyCallResult( bool success, bytes memory returndata, string memory errorMessage ) private pure returns(bytes memory) { if (success) { return returndata; } else { if (returndata.length > 0) { // solhint-disable-next-line no-inline-assembly assembly { let returndata_size := mload(returndata) revert(add(32, returndata), returndata_size) } } else { revert(errorMessage); } } } } contract OwnableData { address public owner; address public pendingOwner; } contract Ownable is OwnableData { event OwnershipTransferred(address indexed previousOwner, address indexed newOwner); /// @notice `owner` defaults to msg.sender on construction. constructor() { owner = msg.sender; emit OwnershipTransferred(address(0), msg.sender); } /// @notice Transfers ownership to `newOwner`. Either directly or claimable by the new pending owner. /// Can only be invoked by the current `owner`. /// @param newOwner Address of the new owner. /// @param direct True if `newOwner` should be set immediately. False if `newOwner` needs to use `claimOwnership`. /// @param renounce Allows the `newOwner` to be `address(0)` if `direct` and `renounce` is True. Has no effect otherwise. function transferOwnership( address newOwner, bool direct, bool renounce ) public onlyOwner { if (direct) { // Checks require(newOwner != address(0) || renounce, "Ownable: zero address"); // Effects emit OwnershipTransferred(owner, newOwner); owner = newOwner; pendingOwner = address(0); } else { // Effects pendingOwner = newOwner; } } /// @notice Needs to be called by `pendingOwner` to claim ownership. function claimOwnership() public { address _pendingOwner = pendingOwner; // Checks require(msg.sender == _pendingOwner, "Ownable: caller != pending owner"); // Effects emit OwnershipTransferred(owner, _pendingOwner); owner = _pendingOwner; pendingOwner = address(0); } /// @notice Only allows the `owner` to execute the function. modifier onlyOwner() { require(msg.sender == owner, "Ownable: caller is not the owner"); _; } } interface IERC20 { function decimals() external view returns (uint8); function balanceOf(address account) external view returns (uint256); function transfer(address recipient, uint256 amount) external returns (bool); function approve(address spender, uint256 amount) external returns (bool); function totalSupply() external view returns (uint256); 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); } library SafeERC20 { using LowGasSafeMath for uint256; using Address for address; function safeTransfer(IERC20 token, address to, uint256 value) internal { _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value)); } function safeTransferFrom(IERC20 token, address from, address to, uint256 value) internal { _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value)); } function _callOptionalReturn(IERC20 token, bytes memory data) private { bytes memory returndata = address(token).functionCall(data, "SafeERC20: low-level call failed"); if (returndata.length > 0) { // Return data is optional // solhint-disable-next-line max-line-length require(abi.decode(returndata, (bool)), "SafeERC20: ERC20 operation did not succeed"); } } } interface IERC20Mintable { function mint( uint256 amount_ ) external; function mint( address account_, uint256 ammount_ ) external; } interface ITIMEERC20 is IERC20Mintable, IERC20 { function burnFrom(address account_, uint256 amount_) external; } interface IBondCalculator { function valuation( address pair_, uint amount_ ) external view returns ( uint _value ); } contract TimeTreasury is Ownable { using LowGasSafeMath for uint; using LowGasSafeMath for uint32; using SafeERC20 for IERC20; event Deposit( address indexed token, uint amount, uint value ); event Withdrawal( address indexed token, uint amount, uint value ); event CreateDebt( address indexed debtor, address indexed token, uint amount, uint value ); event RepayDebt( address indexed debtor, address indexed token, uint amount, uint value ); event ReservesManaged( address indexed token, uint amount ); event ReservesUpdated( uint indexed totalReserves ); event ReservesAudited( uint indexed totalReserves ); event RewardsMinted( address indexed caller, address indexed recipient, uint amount ); event ChangeQueued( MANAGING indexed managing, address queued ); event ChangeActivated( MANAGING indexed managing, address activated, bool result ); event ChangeLimitAmount( uint256 amount ); enum MANAGING { RESERVEDEPOSITOR, RESERVESPENDER, RESERVETOKEN, RESERVEMANAGER, LIQUIDITYDEPOSITOR, LIQUIDITYTOKEN, LIQUIDITYMANAGER, DEBTOR, REWARDMANAGER, SOHM } ITIMEERC20 public immutable Time; uint32 public immutable secondsNeededForQueue; address[] public reserveTokens; // Push only, beware false-positives. mapping( address => bool ) public isReserveToken; mapping( address => uint32 ) public reserveTokenQueue; // Delays changes to mapping. address[] public reserveDepositors; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isReserveDepositor; mapping( address => uint32 ) public reserveDepositorQueue; // Delays changes to mapping. address[] public reserveSpenders; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isReserveSpender; mapping( address => uint32 ) public reserveSpenderQueue; // Delays changes to mapping. address[] public liquidityTokens; // Push only, beware false-positives. mapping( address => bool ) public isLiquidityToken; mapping( address => uint32 ) public LiquidityTokenQueue; // Delays changes to mapping. address[] public liquidityDepositors; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isLiquidityDepositor; mapping( address => uint32 ) public LiquidityDepositorQueue; // Delays changes to mapping. mapping( address => address ) public bondCalculator; // bond calculator for liquidity token address[] public reserveManagers; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isReserveManager; mapping( address => uint32 ) public ReserveManagerQueue; // Delays changes to mapping. address[] public liquidityManagers; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isLiquidityManager; mapping( address => uint32 ) public LiquidityManagerQueue; // Delays changes to mapping. address[] public debtors; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isDebtor; mapping( address => uint32 ) public debtorQueue; // Delays changes to mapping. mapping( address => uint ) public debtorBalance; address[] public rewardManagers; // Push only, beware false-positives. Only for viewing. mapping( address => bool ) public isRewardManager; mapping( address => uint32 ) public rewardManagerQueue; // Delays changes to mapping. IERC20 public MEMOries; uint public sOHMQueue; // Delays change to sOHM address uint public totalReserves; // Risk-free value of all assets uint public totalDebt; constructor ( address _Time, address _MIM, uint32 _secondsNeededForQueue ) { require( _Time != address(0) ); Time = ITIMEERC20(_Time); isReserveToken[ _MIM ] = true; reserveTokens.push( _MIM ); // isLiquidityToken[ _OHMDAI ] = true; // liquidityTokens.push( _OHMDAI ); secondsNeededForQueue = _secondsNeededForQueue; } /** @notice allow approved address to deposit an asset for Time @param _amount uint @param _token address @param _profit uint @return send_ uint */ function deposit( uint _amount, address _token, uint _profit ) external returns ( uint send_ ) { require( isReserveToken[ _token ] || isLiquidityToken[ _token ], "Not accepted" ); IERC20( _token ).safeTransferFrom( msg.sender, address(this), _amount ); if ( isReserveToken[ _token ] ) { require( isReserveDepositor[ msg.sender ], "Not approved" ); } else { require( isLiquidityDepositor[ msg.sender ], "Not approved" ); } uint value = valueOfToken(_token, _amount); // mint Time needed and store amount of rewards for distribution send_ = value.sub( _profit ); Time.mint( msg.sender, send_ ); totalReserves = totalReserves.add( value ); emit ReservesUpdated( totalReserves ); emit Deposit( _token, _amount, value ); } /** @notice allow approved address to burn Time for reserves @param _amount uint @param _token address */ function withdraw( uint _amount, address _token ) external { require( isReserveToken[ _token ], "Not accepted" ); // Only reserves can be used for redemptions require( isReserveSpender[ msg.sender ], "Not approved" ); uint value = valueOfToken( _token, _amount ); Time.burnFrom( msg.sender, value ); totalReserves = totalReserves.sub( value ); emit ReservesUpdated( totalReserves ); IERC20( _token ).safeTransfer( msg.sender, _amount ); emit Withdrawal( _token, _amount, value ); } /** @notice allow approved address to borrow reserves @param _amount uint @param _token address */ function incurDebt( uint _amount, address _token ) external { require( isDebtor[ msg.sender ], "Not approved" ); require( isReserveToken[ _token ], "Not accepted" ); uint value = valueOfToken( _token, _amount ); uint maximumDebt = MEMOries.balanceOf( msg.sender ); // Can only borrow against sOHM held uint balance = debtorBalance[ msg.sender ]; uint availableDebt = maximumDebt.sub( balance ); require( value <= availableDebt, "Exceeds debt limit" ); debtorBalance[ msg.sender ] = balance.add( value ); totalDebt = totalDebt.add( value ); totalReserves = totalReserves.sub( value ); emit ReservesUpdated( totalReserves ); IERC20( _token ).safeTransfer( msg.sender, _amount ); emit CreateDebt( msg.sender, _token, _amount, value ); } /** @notice allow approved address to repay borrowed reserves with reserves @param _amount uint @param _token address */ function repayDebtWithReserve( uint _amount, address _token ) external { require( isDebtor[ msg.sender ], "Not approved" ); require( isReserveToken[ _token ], "Not accepted" ); IERC20( _token ).safeTransferFrom( msg.sender, address(this), _amount ); uint value = valueOfToken( _token, _amount ); debtorBalance[ msg.sender ] = debtorBalance[ msg.sender ].sub( value ); totalDebt = totalDebt.sub( value ); totalReserves = totalReserves.add( value ); emit ReservesUpdated( totalReserves ); emit RepayDebt( msg.sender, _token, _amount, value ); } /** @notice allow approved address to repay borrowed reserves with Time @param _amount uint */ function repayDebtWithTime( uint _amount ) external { require( isDebtor[ msg.sender ], "Not approved as debtor" ); require( isReserveSpender[ msg.sender ], "Not approved as spender" ); Time.burnFrom( msg.sender, _amount ); debtorBalance[ msg.sender ] = debtorBalance[ msg.sender ].sub( _amount ); totalDebt = totalDebt.sub( _amount ); emit RepayDebt( msg.sender, address(Time), _amount, _amount ); } /** @notice allow approved address to withdraw assets @param _token address @param _amount uint */ function manage( address _token, uint _amount ) external { uint value = valueOfToken(_token, _amount); if( isLiquidityToken[ _token ] ) { require( isLiquidityManager[ msg.sender ], "Not approved" ); require(value <= excessReserves()); } else { if (isReserveToken[ _token ]) require(value <= excessReserves()); require( isReserveManager[ msg.sender ], "Not approved" ); } totalReserves = totalReserves.sub( value ); emit ReservesUpdated( totalReserves ); IERC20( _token ).safeTransfer( msg.sender, _amount ); emit ReservesManaged( _token, _amount ); } /** @notice send epoch reward to staking contract */ function mintRewards( address _recipient, uint _amount ) external { require( isRewardManager[ msg.sender ], "Not approved" ); require( _amount <= excessReserves(), "Insufficient reserves" ); Time.mint( _recipient, _amount ); emit RewardsMinted( msg.sender, _recipient, _amount ); } /** @notice returns excess reserves not backing tokens @return uint */ function excessReserves() public view returns ( uint ) { return totalReserves.sub( Time.totalSupply().sub( totalDebt ) ); } /** @notice takes inventory of all tracked assets @notice always consolidate to recognized reserves before audit */ function auditReserves() external onlyOwner { uint reserves; for( uint i = 0; i < reserveTokens.length; i++ ) { reserves = reserves.add ( valueOfToken( reserveTokens[ i ], IERC20( reserveTokens[ i ] ).balanceOf( address(this) ) ) ); } for( uint i = 0; i < liquidityTokens.length; i++ ) { reserves = reserves.add ( valueOfToken( liquidityTokens[ i ], IERC20( liquidityTokens[ i ] ).balanceOf( address(this) ) ) ); } totalReserves = reserves; emit ReservesUpdated( reserves ); emit ReservesAudited( reserves ); } /** @notice returns Time valuation of asset @param _token address @param _amount uint @return value_ uint */ function valueOfToken( address _token, uint _amount ) public view returns ( uint value_ ) { if ( isReserveToken[ _token ] ) { // convert amount to match Time decimals value_ = _amount.mul( 10 ** Time.decimals() ).div( 10 ** IERC20( _token ).decimals() ); } else if ( isLiquidityToken[ _token ] ) { value_ = IBondCalculator( bondCalculator[ _token ] ).valuation( _token, _amount ); } } /** @notice queue address to change boolean in mapping @param _managing MANAGING @param _address address @return bool */ function queue( MANAGING _managing, address _address ) external onlyOwner returns ( bool ) { require( _address != address(0), "IA" ); if ( _managing == MANAGING.RESERVEDEPOSITOR ) { // 0 reserveDepositorQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.RESERVESPENDER ) { // 1 reserveSpenderQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.RESERVETOKEN ) { // 2 reserveTokenQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.RESERVEMANAGER ) { // 3 ReserveManagerQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue.mul32( 2 ) ); } else if ( _managing == MANAGING.LIQUIDITYDEPOSITOR ) { // 4 LiquidityDepositorQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.LIQUIDITYTOKEN ) { // 5 LiquidityTokenQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.LIQUIDITYMANAGER ) { // 6 LiquidityManagerQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue.mul32( 2 ) ); } else if ( _managing == MANAGING.DEBTOR ) { // 7 debtorQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.REWARDMANAGER ) { // 8 rewardManagerQueue[ _address ] = uint32(block.timestamp).add32( secondsNeededForQueue ); } else if ( _managing == MANAGING.SOHM ) { // 9 sOHMQueue = uint32(block.timestamp).add32( secondsNeededForQueue ); } else return false; emit ChangeQueued( _managing, _address ); return true; } /** @notice verify queue then set boolean in mapping @param _managing MANAGING @param _address address @param _calculator address @return bool */ function toggle( MANAGING _managing, address _address, address _calculator ) external onlyOwner returns ( bool ) { require( _address != address(0), "IA" ); bool result; if ( _managing == MANAGING.RESERVEDEPOSITOR ) { // 0 if ( requirements( reserveDepositorQueue, isReserveDepositor, _address ) ) { reserveDepositorQueue[ _address ] = 0; if( !listContains( reserveDepositors, _address ) ) { reserveDepositors.push( _address ); } } result = !isReserveDepositor[ _address ]; isReserveDepositor[ _address ] = result; } else if ( _managing == MANAGING.RESERVESPENDER ) { // 1 if ( requirements( reserveSpenderQueue, isReserveSpender, _address ) ) { reserveSpenderQueue[ _address ] = 0; if( !listContains( reserveSpenders, _address ) ) { reserveSpenders.push( _address ); } } result = !isReserveSpender[ _address ]; isReserveSpender[ _address ] = result; } else if ( _managing == MANAGING.RESERVETOKEN ) { // 2 if ( requirements( reserveTokenQueue, isReserveToken, _address ) ) { reserveTokenQueue[ _address ] = 0; if( !listContains( reserveTokens, _address ) && !listContains( liquidityTokens, _address ) ) { reserveTokens.push( _address ); } } result = !isReserveToken[ _address ]; require(!result || !isLiquidityToken[_address], "Do not add to both types of token"); isReserveToken[ _address ] = result; } else if ( _managing == MANAGING.RESERVEMANAGER ) { // 3 if ( requirements( ReserveManagerQueue, isReserveManager, _address ) ) { reserveManagers.push( _address ); ReserveManagerQueue[ _address ] = 0; if( !listContains( reserveManagers, _address ) ) { reserveManagers.push( _address ); } } result = !isReserveManager[ _address ]; isReserveManager[ _address ] = result; } else if ( _managing == MANAGING.LIQUIDITYDEPOSITOR ) { // 4 if ( requirements( LiquidityDepositorQueue, isLiquidityDepositor, _address ) ) { liquidityDepositors.push( _address ); LiquidityDepositorQueue[ _address ] = 0; if( !listContains( liquidityDepositors, _address ) ) { liquidityDepositors.push( _address ); } } result = !isLiquidityDepositor[ _address ]; isLiquidityDepositor[ _address ] = result; } else if ( _managing == MANAGING.LIQUIDITYTOKEN ) { // 5 if ( requirements( LiquidityTokenQueue, isLiquidityToken, _address ) ) { LiquidityTokenQueue[ _address ] = 0; if( !listContains( liquidityTokens, _address ) && !listContains( reserveTokens, _address ) ) { liquidityTokens.push( _address ); } } result = !isLiquidityToken[ _address ]; require(!result || !isReserveToken[_address], "Do not add to both types of token"); isLiquidityToken[ _address ] = result; bondCalculator[ _address ] = _calculator; } else if ( _managing == MANAGING.LIQUIDITYMANAGER ) { // 6 if ( requirements( LiquidityManagerQueue, isLiquidityManager, _address ) ) { LiquidityManagerQueue[ _address ] = 0; if( !listContains( liquidityManagers, _address ) ) { liquidityManagers.push( _address ); } } result = !isLiquidityManager[ _address ]; isLiquidityManager[ _address ] = result; } else if ( _managing == MANAGING.DEBTOR ) { // 7 if ( requirements( debtorQueue, isDebtor, _address ) ) { debtorQueue[ _address ] = 0; if( !listContains( debtors, _address ) ) { debtors.push( _address ); } } result = !isDebtor[ _address ]; isDebtor[ _address ] = result; } else if ( _managing == MANAGING.REWARDMANAGER ) { // 8 if ( requirements( rewardManagerQueue, isRewardManager, _address ) ) { rewardManagerQueue[ _address ] = 0; if( !listContains( rewardManagers, _address ) ) { rewardManagers.push( _address ); } } result = !isRewardManager[ _address ]; isRewardManager[ _address ] = result; } else if ( _managing == MANAGING.SOHM ) { // 9 sOHMQueue = 0; MEMOries = IERC20(_address); result = true; } else return false; emit ChangeActivated( _managing, _address, result ); return true; } /** @notice checks requirements and returns altered structs @param queue_ mapping( address => uint ) @param status_ mapping( address => bool ) @param _address address @return bool */ function requirements( mapping( address => uint32 ) storage queue_, mapping( address => bool ) storage status_, address _address ) internal view returns ( bool ) { if ( !status_[ _address ] ) { require( queue_[ _address ] != 0, "Must queue" ); require( queue_[ _address ] <= uint32(block.timestamp), "Queue not expired" ); return true; } return false; } /** @notice checks array to ensure against duplicate @param _list address[] @param _token address @return bool */ function listContains( address[] storage _list, address _token ) internal view returns ( bool ) { for( uint i = 0; i < _list.length; i++ ) { if( _list[ i ] == _token ) { return true; } } return false; } }
Contract ABI
[{"type":"constructor","stateMutability":"nonpayable","inputs":[{"type":"address","name":"_Time","internalType":"address"},{"type":"address","name":"_MIM","internalType":"address"},{"type":"uint32","name":"_secondsNeededForQueue","internalType":"uint32"}]},{"type":"event","name":"ChangeActivated","inputs":[{"type":"uint8","name":"managing","internalType":"enum TimeTreasury.MANAGING","indexed":true},{"type":"address","name":"activated","internalType":"address","indexed":false},{"type":"bool","name":"result","internalType":"bool","indexed":false}],"anonymous":false},{"type":"event","name":"ChangeLimitAmount","inputs":[{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"ChangeQueued","inputs":[{"type":"uint8","name":"managing","internalType":"enum TimeTreasury.MANAGING","indexed":true},{"type":"address","name":"queued","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"CreateDebt","inputs":[{"type":"address","name":"debtor","internalType":"address","indexed":true},{"type":"address","name":"token","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"Deposit","inputs":[{"type":"address","name":"token","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"OwnershipTransferred","inputs":[{"type":"address","name":"previousOwner","internalType":"address","indexed":true},{"type":"address","name":"newOwner","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"RepayDebt","inputs":[{"type":"address","name":"debtor","internalType":"address","indexed":true},{"type":"address","name":"token","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"ReservesAudited","inputs":[{"type":"uint256","name":"totalReserves","internalType":"uint256","indexed":true}],"anonymous":false},{"type":"event","name":"ReservesManaged","inputs":[{"type":"address","name":"token","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"ReservesUpdated","inputs":[{"type":"uint256","name":"totalReserves","internalType":"uint256","indexed":true}],"anonymous":false},{"type":"event","name":"RewardsMinted","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true},{"type":"address","name":"recipient","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"Withdrawal","inputs":[{"type":"address","name":"token","internalType":"address","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"LiquidityDepositorQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"LiquidityManagerQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"LiquidityTokenQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"contract IERC20"}],"name":"MEMOries","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"ReserveManagerQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"contract ITIMEERC20"}],"name":"Time","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"auditReserves","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"bondCalculator","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"claimOwnership","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"debtorBalance","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"debtorQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"debtors","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"uint256","name":"send_","internalType":"uint256"}],"name":"deposit","inputs":[{"type":"uint256","name":"_amount","internalType":"uint256"},{"type":"address","name":"_token","internalType":"address"},{"type":"uint256","name":"_profit","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"excessReserves","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"incurDebt","inputs":[{"type":"uint256","name":"_amount","internalType":"uint256"},{"type":"address","name":"_token","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isDebtor","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isLiquidityDepositor","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isLiquidityManager","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isLiquidityToken","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isReserveDepositor","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isReserveManager","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isReserveSpender","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isReserveToken","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isRewardManager","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"liquidityDepositors","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"liquidityManagers","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"liquidityTokens","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"manage","inputs":[{"type":"address","name":"_token","internalType":"address"},{"type":"uint256","name":"_amount","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"mintRewards","inputs":[{"type":"address","name":"_recipient","internalType":"address"},{"type":"uint256","name":"_amount","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"owner","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"pendingOwner","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"queue","inputs":[{"type":"uint8","name":"_managing","internalType":"enum TimeTreasury.MANAGING"},{"type":"address","name":"_address","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"repayDebtWithReserve","inputs":[{"type":"uint256","name":"_amount","internalType":"uint256"},{"type":"address","name":"_token","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"repayDebtWithTime","inputs":[{"type":"uint256","name":"_amount","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"reserveDepositorQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"reserveDepositors","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"reserveManagers","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"reserveSpenderQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"reserveSpenders","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"reserveTokenQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"reserveTokens","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"rewardManagerQueue","inputs":[{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"rewardManagers","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"sOHMQueue","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint32","name":"","internalType":"uint32"}],"name":"secondsNeededForQueue","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"toggle","inputs":[{"type":"uint8","name":"_managing","internalType":"enum TimeTreasury.MANAGING"},{"type":"address","name":"_address","internalType":"address"},{"type":"address","name":"_calculator","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalDebt","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalReserves","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferOwnership","inputs":[{"type":"address","name":"newOwner","internalType":"address"},{"type":"bool","name":"direct","internalType":"bool"},{"type":"bool","name":"renounce","internalType":"bool"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"value_","internalType":"uint256"}],"name":"valueOfToken","inputs":[{"type":"address","name":"_token","internalType":"address"},{"type":"uint256","name":"_amount","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"withdraw","inputs":[{"type":"uint256","name":"_amount","internalType":"uint256"},{"type":"address","name":"_token","internalType":"address"}]}]
Contract Creation Code
0x60c060405234801561001057600080fd5b50604051620037c2380380620037c28339818101604052606081101561003557600080fd5b5080516020820151604092830151600080546001600160a01b0319163390811782559451939492939192917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e0908290a36001600160a01b03831661009857600080fd5b6001600160601b0319606084901b166080526001600160a01b039182166000818152600360205260408120805460ff1916600190811790915560028054918201815582527f405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5ace0180546001600160a01b0319169092179091556001600160e01b031960e083901b1660a052919092169163ffffffff169061362190620001a1903980611637528061203352806120b0528061212d52806121a9528061223b52806122b8528061233452806123b6528061243352806124b0525080610a595280610e90528061152c528061174152806117f55280611aa65280611c98528061256952506136216000f3fe608060405234801561001057600080fd5b50600436106102f05760003560e01c80638f59c7271161019d578063d1b317e5116100e9578063ee4e19a1116100a2578063fbfd393b1161007c578063fbfd393b14610918578063fc7b9c181461094f578063fd1ec01014610957578063fff9ee8714610974576102f0565b8063ee4e19a1146108c4578063f8e157ea146108ea578063fb939588146108f2576102f0565b8063d1b317e5146107e9578063d796ffb814610815578063df89b34414610841578063e30c397814610867578063e83afee31461086f578063ebd83cd81461089e576102f0565b8063ab319c9a11610156578063bc157ac111610130578063bc157ac11461074e578063c24ad43e14610780578063cd85641a146107a6578063d031370b146107cc576102f0565b8063ab319c9a146106e5578063b1bd38b01461070b578063b5b1d56014610731576102f0565b80638f59c727146106285780638f6a7b571461064e5780638f840ddd1461066b578063932cc8c314610673578063a1210a2d14610699578063a569e571146106bf576102f0565b806349880e521161025c57806370a0502a116102155780637b6e5083116101ef5780637b6e5083146105c0578063869871bf146105dd57806387d67dff146105fa5780638da5cb5b14610620576102f0565b806370a0502a1461055c578063788c6c01146105795780637a8960d8146105b8576102f0565b806349880e52146104b75780634e71e0c8146104bf5780634e83423c146104c757806368c31dd5146104ed5780636a20de92146105135780636b5e40a71461053f576102f0565b8063124154ca116102ae578063124154ca146103fe57806312422d23146104385780631af4da70146104645780632789de371461048a5780632b7ce50014610492578063437f79121461049a576102f0565b8062f714ce146102f55780630619aff114610323578063078dfbe71461035c578063094a8651146103925780630b0eee30146103ca5780630c3513a8146103f6575b600080fd5b6103216004803603604081101561030b57600080fd5b50803590602001356001600160a01b031661099a565b005b6103406004803603602081101561033957600080fd5b5035610b6c565b604080516001600160a01b039092168252519081900360200190f35b6103216004803603606081101561037257600080fd5b506001600160a01b03813516906020810135151590604001351515610b96565b6103b8600480360360208110156103a857600080fd5b50356001600160a01b0316610ccc565b60408051918252519081900360200190f35b610321600480360360408110156103e057600080fd5b506001600160a01b038135169060200135610cde565b6103b8610e83565b6104246004803603602081101561041457600080fd5b50356001600160a01b0316610f27565b604080519115158252519081900360200190f35b6103216004803603604081101561044e57600080fd5b50803590602001356001600160a01b0316610f3c565b6103406004803603602081101561047a57600080fd5b50356001600160a01b0316611194565b6103b86111af565b6103216111b5565b610340600480360360208110156104b057600080fd5b5035611378565b610340611388565b610321611397565b610424600480360360208110156104dd57600080fd5b50356001600160a01b0316611459565b6104246004803603602081101561050357600080fd5b50356001600160a01b031661146e565b6103216004803603604081101561052957600080fd5b506001600160a01b038135169060200135611483565b6103406004803603602081101561055557600080fd5b50356115fd565b6103406004803603602081101561057257600080fd5b503561160d565b61059f6004803603602081101561058f57600080fd5b50356001600160a01b031661161d565b6040805163ffffffff9092168252519081900360200190f35b61059f611635565b610321600480360360208110156105d657600080fd5b5035611659565b610340600480360360208110156105f357600080fd5b5035611846565b6104246004803603602081101561061057600080fd5b50356001600160a01b0316611856565b61034061186b565b61059f6004803603602081101561063e57600080fd5b50356001600160a01b031661187a565b6103406004803603602081101561066457600080fd5b5035611892565b6103b86118a2565b61059f6004803603602081101561068957600080fd5b50356001600160a01b03166118a8565b610424600480360360208110156106af57600080fd5b50356001600160a01b03166118c0565b610424600480360360208110156106d557600080fd5b50356001600160a01b03166118d5565b61059f600480360360208110156106fb57600080fd5b50356001600160a01b03166118ea565b61059f6004803603602081101561072157600080fd5b50356001600160a01b0316611902565b6103406004803603602081101561074757600080fd5b503561191a565b6103b86004803603606081101561076457600080fd5b508035906001600160a01b03602082013516906040013561192a565b61059f6004803603602081101561079657600080fd5b50356001600160a01b0316611ba8565b61059f600480360360208110156107bc57600080fd5b50356001600160a01b0316611bc0565b610340600480360360208110156107e257600080fd5b5035611bd8565b6103b8600480360360408110156107ff57600080fd5b506001600160a01b038135169060200135611be8565b6103216004803603604081101561082b57600080fd5b50803590602001356001600160a01b0316611ddc565b6104246004803603602081101561085757600080fd5b50356001600160a01b0316611f5f565b610340611f74565b6104246004803603604081101561088557600080fd5b50803560ff1690602001356001600160a01b0316611f83565b610424600480360360208110156108b457600080fd5b50356001600160a01b031661253d565b610424600480360360208110156108da57600080fd5b50356001600160a01b0316612552565b610340612567565b61059f6004803603602081101561090857600080fd5b50356001600160a01b031661258b565b6104246004803603606081101561092e57600080fd5b5060ff813516906001600160a01b03602082013581169160400135166125a3565b6103b8613000565b6103406004803603602081101561096d57600080fd5b5035613006565b61059f6004803603602081101561098a57600080fd5b50356001600160a01b0316613016565b6001600160a01b03811660009081526003602052604090205460ff166109f6576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b3360009081526009602052604090205460ff16610a49576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6000610a558284611be8565b90507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03166379cc679033836040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015610ace57600080fd5b505af1158015610ae2573d6000803e3d6000fd5b5050602154610af4925090508261302e565b60218190556040516000805160206135a283398151915290600090a2610b246001600160a01b038316338561303e565b604080518481526020810183905281516001600160a01b038516927fdf273cb619d95419a9cd0ec88123a0538c85064229baa6363788f743fff90deb928290030190a2505050565b60128181548110610b7c57600080fd5b6000918252602090912001546001600160a01b0316905081565b6000546001600160a01b03163314610be3576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b8115610cab576001600160a01b038316151580610bfd5750805b610c46576040805162461bcd60e51b81526020600482015260156024820152744f776e61626c653a207a65726f206164647265737360581b604482015290519081900360640190fd5b600080546040516001600160a01b03808716939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b0385166001600160a01b031991821617909155600180549091169055610cc7565b600180546001600160a01b0319166001600160a01b0385161790555b505050565b601b6020526000908152604090205481565b6000610cea8383611be8565b6001600160a01b0384166000908152600c602052604090205490915060ff1615610d7a573360009081526016602052604090205460ff16610d61576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b610d69610e83565b811115610d7557600080fd5b610e02565b6001600160a01b03831660009081526003602052604090205460ff1615610daf57610da3610e83565b811115610daf57600080fd5b3360009081526013602052604090205460ff16610e02576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b602154610e0f908261302e565b60218190556040516000805160206135a283398151915290600090a2610e3f6001600160a01b038416338461303e565b6040805183815290516001600160a01b038516917f2bb2640731848fe9820ba48dbc978c1fc9bbd5f11b948bfab05b7dee3378fd80919081900360200190a2505050565b6000610f22610f196022547f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03166318160ddd6040518163ffffffff1660e01b815260040160206040518083038186803b158015610ee757600080fd5b505afa158015610efb573d6000803e3d6000fd5b505050506040513d6020811015610f1157600080fd5b50519061302e565b6021549061302e565b905090565b60066020526000908152604090205460ff1681565b3360009081526019602052604090205460ff16610f8f576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6001600160a01b03811660009081526003602052604090205460ff16610feb576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b6000610ff78284611be8565b601f54604080516370a0823160e01b815233600482015290519293506000926001600160a01b03909216916370a0823191602480820192602092909190829003018186803b15801561104857600080fd5b505afa15801561105c573d6000803e3d6000fd5b505050506040513d602081101561107257600080fd5b5051336000908152601b6020526040812054919250611091838361302e565b9050808411156110dd576040805162461bcd60e51b8152602060048201526012602482015271115e18d959591cc81919589d081b1a5b5a5d60721b604482015290519081900360640190fd5b6110e78285613090565b336000908152601b60205260409020556022546111049085613090565b602255602154611114908561302e565b60218190556040516000805160206135a283398151915290600090a26111446001600160a01b038616338861303e565b604080518781526020810186905281516001600160a01b0388169233927f7e1a939bed137a819b5d2979822c67f877689f7a863d5e4cb57cdca97b2977d6929081900390910190a3505050505050565b6011602052600090815260409020546001600160a01b031681565b60205481565b6000546001600160a01b03163314611202576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6000805b6002548110156112da576112d06112c96002838154811061122357fe5b600091825260209091200154600280546001600160a01b03909216918590811061124957fe5b60009182526020918290200154604080516370a0823160e01b815230600482015290516001600160a01b03909216926370a0823192602480840193829003018186803b15801561129857600080fd5b505afa1580156112ac573d6000803e3d6000fd5b505050506040513d60208110156112c257600080fd5b5051611be8565b8390613090565b9150600101611206565b5060005b600b5481101561132b576113216112c9600b83815481106112fb57fe5b600091825260209091200154600b80546001600160a01b03909216918590811061124957fe5b91506001016112de565b50602181905560405181906000805160206135a283398151915290600090a260405181907fec691f09f6924b27932253f85caf99bacc30360cc0e50a1cc4d2acc24601446690600090a250565b60088181548110610b7c57600080fd5b601f546001600160a01b031681565b6001546001600160a01b03163381146113f7576040805162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c657220213d2070656e64696e67206f776e6572604482015290519081900360640190fd5b600080546040516001600160a01b03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b039092166001600160a01b0319928316179055600180549091169055565b601d6020526000908152604090205460ff1681565b60036020526000908152604090205460ff1681565b336000908152601d602052604090205460ff166114d6576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6114de610e83565b81111561152a576040805162461bcd60e51b8152602060048201526015602482015274496e73756666696369656e7420726573657276657360581b604482015290519081900360640190fd5b7f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03166340c10f1983836040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b1580156115a157600080fd5b505af11580156115b5573d6000803e3d6000fd5b50506040805184815290516001600160a01b03861693503392507ffa8ccab40e7da8146c2304cd0950334fd30a6ba093abe86261aa13911fed849c9181900360200190a35050565b60058181548110610b7c57600080fd5b60158181548110610b7c57600080fd5b60046020526000908152604090205463ffffffff1681565b7f000000000000000000000000000000000000000000000000000000000000000081565b3360009081526019602052604090205460ff166116b6576040805162461bcd60e51b81526020600482015260166024820152752737ba1030b8383937bb32b21030b9903232b13a37b960511b604482015290519081900360640190fd5b3360009081526009602052604090205460ff1661171a576040805162461bcd60e51b815260206004820152601760248201527f4e6f7420617070726f766564206173207370656e646572000000000000000000604482015290519081900360640190fd5b6040805163079cc67960e41b81523360048201526024810183905290516001600160a01b037f000000000000000000000000000000000000000000000000000000000000000016916379cc679091604480830192600092919082900301818387803b15801561178857600080fd5b505af115801561179c573d6000803e3d6000fd5b5050336000908152601b60205260409020546117bb925090508261302e565b336000908152601b60205260409020556022546117d8908261302e565b602255604080518281526020810183905281516001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169233927fc6d98eecfc9c78ab62c89a82950079b54874749f1f6f24090f7acc758bc2f309929081900390910190a350565b60188181548110610b7c57600080fd5b60096020526000908152604090205460ff1681565b6000546001600160a01b031681565b600d6020526000908152604090205463ffffffff1681565b600e8181548110610b7c57600080fd5b60215481565b60076020526000908152604090205463ffffffff1681565b600f6020526000908152604090205460ff1681565b600c6020526000908152604090205460ff1681565b60176020526000908152604090205463ffffffff1681565b60146020526000908152604090205463ffffffff1681565b601c8181548110610b7c57600080fd5b6001600160a01b03821660009081526003602052604081205460ff168061196957506001600160a01b0383166000908152600c602052604090205460ff165b6119a9576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b6119be6001600160a01b0384163330876130a0565b6001600160a01b03831660009081526003602052604090205460ff1615611a37573360009081526006602052604090205460ff16611a32576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b611a8a565b336000908152600f602052604090205460ff16611a8a576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6000611a968486611be8565b9050611aa2818461302e565b91507f00000000000000000000000000000000000000000000000000000000000000006001600160a01b03166340c10f1933846040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015611b1b57600080fd5b505af1158015611b2f573d6000803e3d6000fd5b5050602154611b419250905082613090565b60218190556040516000805160206135a283398151915290600090a2604080518681526020810183905281516001600160a01b038716927f90890809c654f11d6e72a28fa60149770a0d11ec6c92319d6ceb2bb0a4ea1a15928290030190a2509392505050565b600a6020526000908152604090205463ffffffff1681565b601a6020526000908152604090205463ffffffff1681565b60028181548110610b7c57600080fd5b6001600160a01b03821660009081526003602052604081205460ff1615611d2557611d1e836001600160a01b031663313ce5676040518163ffffffff1660e01b815260040160206040518083038186803b158015611c4557600080fd5b505afa158015611c59573d6000803e3d6000fd5b505050506040513d6020811015611c6f57600080fd5b50516040805163313ce56760e01b8152905160ff909216600a0a91611d18916001600160a01b037f0000000000000000000000000000000000000000000000000000000000000000169163313ce56791600480820192602092909190829003018186803b158015611cdf57600080fd5b505afa158015611cf3573d6000803e3d6000fd5b505050506040513d6020811015611d0957600080fd5b5051859060ff16600a0a613100565b90613124565b9050611dd6565b6001600160a01b0383166000908152600c602052604090205460ff1615611dd6576001600160a01b03808416600081815260116020908152604091829020548251634249719f60e01b815260048101949094526024840187905291519190931692634249719f9260448082019391829003018186803b158015611da757600080fd5b505afa158015611dbb573d6000803e3d6000fd5b505050506040513d6020811015611dd157600080fd5b505190505b92915050565b3360009081526019602052604090205460ff16611e2f576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6001600160a01b03811660009081526003602052604090205460ff16611e8b576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b611ea06001600160a01b0382163330856130a0565b6000611eac8284611be8565b336000908152601b6020526040902054909150611ec9908261302e565b336000908152601b6020526040902055602254611ee6908261302e565b602255602154611ef69082613090565b60218190556040516000805160206135a283398151915290600090a2604080518481526020810183905281516001600160a01b0385169233927fc6d98eecfc9c78ab62c89a82950079b54874749f1f6f24090f7acc758bc2f309929081900390910190a3505050565b60166020526000908152604090205460ff1681565b6001546001600160a01b031681565b600080546001600160a01b03163314611fd1576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6001600160a01b038216612011576040805162461bcd60e51b8152602060048201526002602482015261494160f01b604482015290519081900360640190fd5b600083600981111561201f57fe5b141561208e5761205963ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600760205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600183600981111561209c57fe5b141561210b576120d663ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600a60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600283600981111561211957fe5b14156121885761215363ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600460205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600383600981111561219657fe5b1415612219576121e46121d463ffffffff7f000000000000000000000000000000000000000000000000000000000000000081169060029061315c16565b63ffffffff428116919061314316565b6001600160a01b0383166000908152601460205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600483600981111561222757fe5b14156122965761226163ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601060205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b60058360098111156122a457fe5b1415612313576122de63ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600d60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600683600981111561232157fe5b14156123945761235f6121d463ffffffff7f000000000000000000000000000000000000000000000000000000000000000081169060029061315c16565b6001600160a01b0383166000908152601760205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b60078360098111156123a257fe5b1415612411576123dc63ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601a60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600883600981111561241f57fe5b141561248e5761245963ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601e60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600983600981111561249c57fe5b14156124e4576124d663ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b63ffffffff166020556124ec565b506000611dd6565b8260098111156124f857fe5b604080516001600160a01b038516815290517f0e4f2c4b5bc209d509bc3d49348c787fefadc66a79351b470599ac0f5be52eaf9181900360200190a250600192915050565b60136020526000908152604090205460ff1681565b60196020526000908152604090205460ff1681565b7f000000000000000000000000000000000000000000000000000000000000000081565b601e6020526000908152604090205463ffffffff1681565b600080546001600160a01b031633146125f1576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6001600160a01b038316612631576040805162461bcd60e51b8152602060048201526002602482015261494160f01b604482015290519081900360640190fd5b60008085600981111561264057fe5b141561270657612653600760068661319e565b156126d6576001600160a01b0384166000908152600760205260409020805463ffffffff19169055612686600585613297565b6126d657600580546001810182556000919091527f036b6384b5eca791c62761152d0c79bb0604c104a5fb6f4eb0703f3154bb3db00180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600660205260409020805460ff81161560ff199091168117909155612fa2565b600185600981111561271457fe5b14156127da57612727600a60098661319e565b156127aa576001600160a01b0384166000908152600a60205260409020805463ffffffff1916905561275a600885613297565b6127aa57600880546001810182556000919091527ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee30180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600960205260409020805460ff81161560ff199091168117909155612fa2565b60028560098111156127e857fe5b141561293c576127fb600460038661319e565b15612894576001600160a01b0384166000908152600460205260409020805463ffffffff1916905561282e600285613297565b1580156128435750612841600b85613297565b155b1561289457600280546001810182556000919091527f405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5ace0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b03831660009081526003602052604090205460ff16158015806128d857506001600160a01b0384166000908152600c602052604090205460ff16155b6129135760405162461bcd60e51b81526004018080602001828103825260218152602001806135816021913960400191505060405180910390fd5b6001600160a01b0384166000908152600360205260409020805460ff1916821515179055612fa2565b600385600981111561294a57fe5b1415612a4d5761295d601460138661319e565b15612a1d57601280546001810182557fbb8a6a4669ba250d26cd7a459eca9d215f8307e33aebe50379bc5a3617ec34440180546001600160a01b0319166001600160a01b0387169081179091556000908152601460205260409020805463ffffffff191690556129cd9085613297565b612a1d57601280546001810182556000919091527fbb8a6a4669ba250d26cd7a459eca9d215f8307e33aebe50379bc5a3617ec34440180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601360205260409020805460ff81161560ff199091168117909155612fa2565b6004856009811115612a5b57fe5b1415612b5e57612a6e6010600f8661319e565b15612b2e57600e80546001810182557fbb7b4a454dc3493923482f07822329ed19e8244eff582cc204f8554c3620c3fd0180546001600160a01b0319166001600160a01b0387169081179091556000908152601060205260409020805463ffffffff19169055612ade9085613297565b612b2e57600e80546001810182556000919091527fbb7b4a454dc3493923482f07822329ed19e8244eff582cc204f8554c3620c3fd0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600f60205260409020805460ff81161560ff199091168117909155612fa2565b6005856009811115612b6c57fe5b1415612ce057612b7f600d600c8661319e565b15612c18576001600160a01b0384166000908152600d60205260409020805463ffffffff19169055612bb2600b85613297565b158015612bc75750612bc5600285613297565b155b15612c1857600b80546001810182556000919091527f0175b7a638427703f0dbe7bb9bbf987a2551717b34e79f33b5b1008d1fa01db90180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600c602052604090205460ff1615801580612c5c57506001600160a01b03841660009081526003602052604090205460ff16155b612c975760405162461bcd60e51b81526004018080602001828103825260218152602001806135816021913960400191505060405180910390fd5b6001600160a01b038481166000908152600c60209081526040808320805460ff19168615151790556011909152902080546001600160a01b031916918516919091179055612fa2565b6006856009811115612cee57fe5b1415612db457612d01601760168661319e565b15612d84576001600160a01b0384166000908152601760205260409020805463ffffffff19169055612d34601585613297565b612d8457601580546001810182556000919091527f55f448fdea98c4d29eb340757ef0a66cd03dbb9538908a6a81d96026b71ec4750180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601660205260409020805460ff81161560ff199091168117909155612fa2565b6007856009811115612dc257fe5b1415612e8857612dd5601a60198661319e565b15612e58576001600160a01b0384166000908152601a60205260409020805463ffffffff19169055612e08601885613297565b612e5857601880546001810182556000919091527fb13d2d76d1f4b7be834882e410b3e3a8afaf69f83600ae24db354391d2378d2e0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601960205260409020805460ff81161560ff199091168117909155612fa2565b6008856009811115612e9657fe5b1415612f5c57612ea9601e601d8661319e565b15612f2c576001600160a01b0384166000908152601e60205260409020805463ffffffff19169055612edc601c85613297565b612f2c57601c80546001810182556000919091527f0e4562a10381dec21b205ed72637e6b1b523bdd0e4d4d50af5cd23dd4500a2110180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601d60205260409020805460ff81161560ff199091168117909155612fa2565b6009856009811115612f6a57fe5b1415612f9857506000602055601f80546001600160a01b0319166001600160a01b0385161790556001612fa2565b6000915050612ff9565b846009811115612fae57fe5b604080516001600160a01b0387168152831515602082015281517f0dcacb7e392f3d6a216ed2660e3dcfd40b7793d33591db2ba185a6b8e44fc477929181900390910190a260019150505b9392505050565b60225481565b600b8181548110610b7c57600080fd5b60106020526000908152604090205463ffffffff1681565b80820382811115611dd657600080fd5b604080516001600160a01b038416602482015260448082018490528251808303909101815260649091019091526020810180516001600160e01b031663a9059cbb60e01b179052610cc79084906132e7565b80820182811015611dd657600080fd5b604080516001600160a01b0380861660248301528416604482015260648082018490528251808303909101815260849091019091526020810180516001600160e01b03166323b872dd60e01b1790526130fa9085906132e7565b50505050565b600082158061311b5750508181028183828161311857fe5b04145b611dd657600080fd5b600080821161313257600080fd5b81838161313b57fe5b049392505050565b80820163ffffffff8084169082161015611dd657600080fd5b600063ffffffff8316158061311b57508163ffffffff168363ffffffff1683850292508263ffffffff168161318d57fe5b0463ffffffff1614611dd657600080fd5b6001600160a01b03811660009081526020839052604081205460ff1661328d576001600160a01b03821660009081526020859052604090205463ffffffff1661321b576040805162461bcd60e51b815260206004820152600a6024820152694d75737420717565756560b01b604482015290519081900360640190fd5b6001600160a01b03821660009081526020859052604090205463ffffffff42811691161115613285576040805162461bcd60e51b8152602060048201526011602482015270145d595d59481b9bdd08195e1c1a5c9959607a1b604482015290519081900360640190fd5b506001612ff9565b5060009392505050565b6000805b835481101561328d57826001600160a01b03168482815481106132ba57fe5b6000918252602090912001546001600160a01b031614156132df576001915050611dd6565b60010161329b565b606061333c826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166133989092919063ffffffff16565b805190915015610cc75780806020019051602081101561335b57600080fd5b5051610cc75760405162461bcd60e51b815260040180806020018281038252602a8152602001806135c2602a913960400191505060405180910390fd5b60606133a784846000856133af565b949350505050565b60606133ba8561355a565b61340b576040805162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015290519081900360640190fd5b60006060866001600160a01b031685876040518082805190602001908083835b6020831061344a5780518252601f19909201916020918201910161342b565b6001836020036101000a03801982511681845116808217855250505050505090500191505060006040518083038185875af1925050503d80600081146134ac576040519150601f19603f3d011682016040523d82523d6000602084013e6134b1565b606091505b509150915081156134c55791506133a79050565b8051156134d55780518082602001fd5b8360405162461bcd60e51b81526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561351f578181015183820152602001613507565b50505050905090810190601f16801561354c5780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b3b15159056fe4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572446f206e6f742061646420746f20626f7468207479706573206f6620746f6b656e93bb8edd35984706eee1b92541281f7f62d33c01c5b2ec0929a113603bd21d665361666545524332303a204552433230206f7065726174696f6e20646964206e6f742073756363656564a2646970667358221220bf3fa5833ad71910cd248eb0ee8de8969806bdd8f418ccddf1fd080c8a0d16c064736f6c6343000705003300000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd000000000000000000000000ea32a96608495e54156ae48931a7c20f0dcc1a210000000000000000000000000000000000000000000000000000000000000000
Deployed ByteCode
0x608060405234801561001057600080fd5b50600436106102f05760003560e01c80638f59c7271161019d578063d1b317e5116100e9578063ee4e19a1116100a2578063fbfd393b1161007c578063fbfd393b14610918578063fc7b9c181461094f578063fd1ec01014610957578063fff9ee8714610974576102f0565b8063ee4e19a1146108c4578063f8e157ea146108ea578063fb939588146108f2576102f0565b8063d1b317e5146107e9578063d796ffb814610815578063df89b34414610841578063e30c397814610867578063e83afee31461086f578063ebd83cd81461089e576102f0565b8063ab319c9a11610156578063bc157ac111610130578063bc157ac11461074e578063c24ad43e14610780578063cd85641a146107a6578063d031370b146107cc576102f0565b8063ab319c9a146106e5578063b1bd38b01461070b578063b5b1d56014610731576102f0565b80638f59c727146106285780638f6a7b571461064e5780638f840ddd1461066b578063932cc8c314610673578063a1210a2d14610699578063a569e571146106bf576102f0565b806349880e521161025c57806370a0502a116102155780637b6e5083116101ef5780637b6e5083146105c0578063869871bf146105dd57806387d67dff146105fa5780638da5cb5b14610620576102f0565b806370a0502a1461055c578063788c6c01146105795780637a8960d8146105b8576102f0565b806349880e52146104b75780634e71e0c8146104bf5780634e83423c146104c757806368c31dd5146104ed5780636a20de92146105135780636b5e40a71461053f576102f0565b8063124154ca116102ae578063124154ca146103fe57806312422d23146104385780631af4da70146104645780632789de371461048a5780632b7ce50014610492578063437f79121461049a576102f0565b8062f714ce146102f55780630619aff114610323578063078dfbe71461035c578063094a8651146103925780630b0eee30146103ca5780630c3513a8146103f6575b600080fd5b6103216004803603604081101561030b57600080fd5b50803590602001356001600160a01b031661099a565b005b6103406004803603602081101561033957600080fd5b5035610b6c565b604080516001600160a01b039092168252519081900360200190f35b6103216004803603606081101561037257600080fd5b506001600160a01b03813516906020810135151590604001351515610b96565b6103b8600480360360208110156103a857600080fd5b50356001600160a01b0316610ccc565b60408051918252519081900360200190f35b610321600480360360408110156103e057600080fd5b506001600160a01b038135169060200135610cde565b6103b8610e83565b6104246004803603602081101561041457600080fd5b50356001600160a01b0316610f27565b604080519115158252519081900360200190f35b6103216004803603604081101561044e57600080fd5b50803590602001356001600160a01b0316610f3c565b6103406004803603602081101561047a57600080fd5b50356001600160a01b0316611194565b6103b86111af565b6103216111b5565b610340600480360360208110156104b057600080fd5b5035611378565b610340611388565b610321611397565b610424600480360360208110156104dd57600080fd5b50356001600160a01b0316611459565b6104246004803603602081101561050357600080fd5b50356001600160a01b031661146e565b6103216004803603604081101561052957600080fd5b506001600160a01b038135169060200135611483565b6103406004803603602081101561055557600080fd5b50356115fd565b6103406004803603602081101561057257600080fd5b503561160d565b61059f6004803603602081101561058f57600080fd5b50356001600160a01b031661161d565b6040805163ffffffff9092168252519081900360200190f35b61059f611635565b610321600480360360208110156105d657600080fd5b5035611659565b610340600480360360208110156105f357600080fd5b5035611846565b6104246004803603602081101561061057600080fd5b50356001600160a01b0316611856565b61034061186b565b61059f6004803603602081101561063e57600080fd5b50356001600160a01b031661187a565b6103406004803603602081101561066457600080fd5b5035611892565b6103b86118a2565b61059f6004803603602081101561068957600080fd5b50356001600160a01b03166118a8565b610424600480360360208110156106af57600080fd5b50356001600160a01b03166118c0565b610424600480360360208110156106d557600080fd5b50356001600160a01b03166118d5565b61059f600480360360208110156106fb57600080fd5b50356001600160a01b03166118ea565b61059f6004803603602081101561072157600080fd5b50356001600160a01b0316611902565b6103406004803603602081101561074757600080fd5b503561191a565b6103b86004803603606081101561076457600080fd5b508035906001600160a01b03602082013516906040013561192a565b61059f6004803603602081101561079657600080fd5b50356001600160a01b0316611ba8565b61059f600480360360208110156107bc57600080fd5b50356001600160a01b0316611bc0565b610340600480360360208110156107e257600080fd5b5035611bd8565b6103b8600480360360408110156107ff57600080fd5b506001600160a01b038135169060200135611be8565b6103216004803603604081101561082b57600080fd5b50803590602001356001600160a01b0316611ddc565b6104246004803603602081101561085757600080fd5b50356001600160a01b0316611f5f565b610340611f74565b6104246004803603604081101561088557600080fd5b50803560ff1690602001356001600160a01b0316611f83565b610424600480360360208110156108b457600080fd5b50356001600160a01b031661253d565b610424600480360360208110156108da57600080fd5b50356001600160a01b0316612552565b610340612567565b61059f6004803603602081101561090857600080fd5b50356001600160a01b031661258b565b6104246004803603606081101561092e57600080fd5b5060ff813516906001600160a01b03602082013581169160400135166125a3565b6103b8613000565b6103406004803603602081101561096d57600080fd5b5035613006565b61059f6004803603602081101561098a57600080fd5b50356001600160a01b0316613016565b6001600160a01b03811660009081526003602052604090205460ff166109f6576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b3360009081526009602052604090205460ff16610a49576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6000610a558284611be8565b90507f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd6001600160a01b03166379cc679033836040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015610ace57600080fd5b505af1158015610ae2573d6000803e3d6000fd5b5050602154610af4925090508261302e565b60218190556040516000805160206135a283398151915290600090a2610b246001600160a01b038316338561303e565b604080518481526020810183905281516001600160a01b038516927fdf273cb619d95419a9cd0ec88123a0538c85064229baa6363788f743fff90deb928290030190a2505050565b60128181548110610b7c57600080fd5b6000918252602090912001546001600160a01b0316905081565b6000546001600160a01b03163314610be3576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b8115610cab576001600160a01b038316151580610bfd5750805b610c46576040805162461bcd60e51b81526020600482015260156024820152744f776e61626c653a207a65726f206164647265737360581b604482015290519081900360640190fd5b600080546040516001600160a01b03808716939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b0385166001600160a01b031991821617909155600180549091169055610cc7565b600180546001600160a01b0319166001600160a01b0385161790555b505050565b601b6020526000908152604090205481565b6000610cea8383611be8565b6001600160a01b0384166000908152600c602052604090205490915060ff1615610d7a573360009081526016602052604090205460ff16610d61576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b610d69610e83565b811115610d7557600080fd5b610e02565b6001600160a01b03831660009081526003602052604090205460ff1615610daf57610da3610e83565b811115610daf57600080fd5b3360009081526013602052604090205460ff16610e02576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b602154610e0f908261302e565b60218190556040516000805160206135a283398151915290600090a2610e3f6001600160a01b038416338461303e565b6040805183815290516001600160a01b038516917f2bb2640731848fe9820ba48dbc978c1fc9bbd5f11b948bfab05b7dee3378fd80919081900360200190a2505050565b6000610f22610f196022547f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd6001600160a01b03166318160ddd6040518163ffffffff1660e01b815260040160206040518083038186803b158015610ee757600080fd5b505afa158015610efb573d6000803e3d6000fd5b505050506040513d6020811015610f1157600080fd5b50519061302e565b6021549061302e565b905090565b60066020526000908152604090205460ff1681565b3360009081526019602052604090205460ff16610f8f576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6001600160a01b03811660009081526003602052604090205460ff16610feb576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b6000610ff78284611be8565b601f54604080516370a0823160e01b815233600482015290519293506000926001600160a01b03909216916370a0823191602480820192602092909190829003018186803b15801561104857600080fd5b505afa15801561105c573d6000803e3d6000fd5b505050506040513d602081101561107257600080fd5b5051336000908152601b6020526040812054919250611091838361302e565b9050808411156110dd576040805162461bcd60e51b8152602060048201526012602482015271115e18d959591cc81919589d081b1a5b5a5d60721b604482015290519081900360640190fd5b6110e78285613090565b336000908152601b60205260409020556022546111049085613090565b602255602154611114908561302e565b60218190556040516000805160206135a283398151915290600090a26111446001600160a01b038616338861303e565b604080518781526020810186905281516001600160a01b0388169233927f7e1a939bed137a819b5d2979822c67f877689f7a863d5e4cb57cdca97b2977d6929081900390910190a3505050505050565b6011602052600090815260409020546001600160a01b031681565b60205481565b6000546001600160a01b03163314611202576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6000805b6002548110156112da576112d06112c96002838154811061122357fe5b600091825260209091200154600280546001600160a01b03909216918590811061124957fe5b60009182526020918290200154604080516370a0823160e01b815230600482015290516001600160a01b03909216926370a0823192602480840193829003018186803b15801561129857600080fd5b505afa1580156112ac573d6000803e3d6000fd5b505050506040513d60208110156112c257600080fd5b5051611be8565b8390613090565b9150600101611206565b5060005b600b5481101561132b576113216112c9600b83815481106112fb57fe5b600091825260209091200154600b80546001600160a01b03909216918590811061124957fe5b91506001016112de565b50602181905560405181906000805160206135a283398151915290600090a260405181907fec691f09f6924b27932253f85caf99bacc30360cc0e50a1cc4d2acc24601446690600090a250565b60088181548110610b7c57600080fd5b601f546001600160a01b031681565b6001546001600160a01b03163381146113f7576040805162461bcd60e51b815260206004820181905260248201527f4f776e61626c653a2063616c6c657220213d2070656e64696e67206f776e6572604482015290519081900360640190fd5b600080546040516001600160a01b03808516939216917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e091a3600080546001600160a01b039092166001600160a01b0319928316179055600180549091169055565b601d6020526000908152604090205460ff1681565b60036020526000908152604090205460ff1681565b336000908152601d602052604090205460ff166114d6576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6114de610e83565b81111561152a576040805162461bcd60e51b8152602060048201526015602482015274496e73756666696369656e7420726573657276657360581b604482015290519081900360640190fd5b7f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd6001600160a01b03166340c10f1983836040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b1580156115a157600080fd5b505af11580156115b5573d6000803e3d6000fd5b50506040805184815290516001600160a01b03861693503392507ffa8ccab40e7da8146c2304cd0950334fd30a6ba093abe86261aa13911fed849c9181900360200190a35050565b60058181548110610b7c57600080fd5b60158181548110610b7c57600080fd5b60046020526000908152604090205463ffffffff1681565b7f000000000000000000000000000000000000000000000000000000000000000081565b3360009081526019602052604090205460ff166116b6576040805162461bcd60e51b81526020600482015260166024820152752737ba1030b8383937bb32b21030b9903232b13a37b960511b604482015290519081900360640190fd5b3360009081526009602052604090205460ff1661171a576040805162461bcd60e51b815260206004820152601760248201527f4e6f7420617070726f766564206173207370656e646572000000000000000000604482015290519081900360640190fd5b6040805163079cc67960e41b81523360048201526024810183905290516001600160a01b037f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd16916379cc679091604480830192600092919082900301818387803b15801561178857600080fd5b505af115801561179c573d6000803e3d6000fd5b5050336000908152601b60205260409020546117bb925090508261302e565b336000908152601b60205260409020556022546117d8908261302e565b602255604080518281526020810183905281516001600160a01b037f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd169233927fc6d98eecfc9c78ab62c89a82950079b54874749f1f6f24090f7acc758bc2f309929081900390910190a350565b60188181548110610b7c57600080fd5b60096020526000908152604090205460ff1681565b6000546001600160a01b031681565b600d6020526000908152604090205463ffffffff1681565b600e8181548110610b7c57600080fd5b60215481565b60076020526000908152604090205463ffffffff1681565b600f6020526000908152604090205460ff1681565b600c6020526000908152604090205460ff1681565b60176020526000908152604090205463ffffffff1681565b60146020526000908152604090205463ffffffff1681565b601c8181548110610b7c57600080fd5b6001600160a01b03821660009081526003602052604081205460ff168061196957506001600160a01b0383166000908152600c602052604090205460ff165b6119a9576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b6119be6001600160a01b0384163330876130a0565b6001600160a01b03831660009081526003602052604090205460ff1615611a37573360009081526006602052604090205460ff16611a32576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b611a8a565b336000908152600f602052604090205460ff16611a8a576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6000611a968486611be8565b9050611aa2818461302e565b91507f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd6001600160a01b03166340c10f1933846040518363ffffffff1660e01b815260040180836001600160a01b0316815260200182815260200192505050600060405180830381600087803b158015611b1b57600080fd5b505af1158015611b2f573d6000803e3d6000fd5b5050602154611b419250905082613090565b60218190556040516000805160206135a283398151915290600090a2604080518681526020810183905281516001600160a01b038716927f90890809c654f11d6e72a28fa60149770a0d11ec6c92319d6ceb2bb0a4ea1a15928290030190a2509392505050565b600a6020526000908152604090205463ffffffff1681565b601a6020526000908152604090205463ffffffff1681565b60028181548110610b7c57600080fd5b6001600160a01b03821660009081526003602052604081205460ff1615611d2557611d1e836001600160a01b031663313ce5676040518163ffffffff1660e01b815260040160206040518083038186803b158015611c4557600080fd5b505afa158015611c59573d6000803e3d6000fd5b505050506040513d6020811015611c6f57600080fd5b50516040805163313ce56760e01b8152905160ff909216600a0a91611d18916001600160a01b037f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd169163313ce56791600480820192602092909190829003018186803b158015611cdf57600080fd5b505afa158015611cf3573d6000803e3d6000fd5b505050506040513d6020811015611d0957600080fd5b5051859060ff16600a0a613100565b90613124565b9050611dd6565b6001600160a01b0383166000908152600c602052604090205460ff1615611dd6576001600160a01b03808416600081815260116020908152604091829020548251634249719f60e01b815260048101949094526024840187905291519190931692634249719f9260448082019391829003018186803b158015611da757600080fd5b505afa158015611dbb573d6000803e3d6000fd5b505050506040513d6020811015611dd157600080fd5b505190505b92915050565b3360009081526019602052604090205460ff16611e2f576040805162461bcd60e51b815260206004820152600c60248201526b139bdd08185c1c1c9bdd995960a21b604482015290519081900360640190fd5b6001600160a01b03811660009081526003602052604090205460ff16611e8b576040805162461bcd60e51b815260206004820152600c60248201526b139bdd081858d8d95c1d195960a21b604482015290519081900360640190fd5b611ea06001600160a01b0382163330856130a0565b6000611eac8284611be8565b336000908152601b6020526040902054909150611ec9908261302e565b336000908152601b6020526040902055602254611ee6908261302e565b602255602154611ef69082613090565b60218190556040516000805160206135a283398151915290600090a2604080518481526020810183905281516001600160a01b0385169233927fc6d98eecfc9c78ab62c89a82950079b54874749f1f6f24090f7acc758bc2f309929081900390910190a3505050565b60166020526000908152604090205460ff1681565b6001546001600160a01b031681565b600080546001600160a01b03163314611fd1576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6001600160a01b038216612011576040805162461bcd60e51b8152602060048201526002602482015261494160f01b604482015290519081900360640190fd5b600083600981111561201f57fe5b141561208e5761205963ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600760205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600183600981111561209c57fe5b141561210b576120d663ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600a60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600283600981111561211957fe5b14156121885761215363ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600460205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600383600981111561219657fe5b1415612219576121e46121d463ffffffff7f000000000000000000000000000000000000000000000000000000000000000081169060029061315c16565b63ffffffff428116919061314316565b6001600160a01b0383166000908152601460205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600483600981111561222757fe5b14156122965761226163ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601060205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b60058360098111156122a457fe5b1415612313576122de63ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152600d60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600683600981111561232157fe5b14156123945761235f6121d463ffffffff7f000000000000000000000000000000000000000000000000000000000000000081169060029061315c16565b6001600160a01b0383166000908152601760205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b60078360098111156123a257fe5b1415612411576123dc63ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601a60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600883600981111561241f57fe5b141561248e5761245963ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b6001600160a01b0383166000908152601e60205260409020805463ffffffff191663ffffffff929092169190911790556124ec565b600983600981111561249c57fe5b14156124e4576124d663ffffffff428116907f00000000000000000000000000000000000000000000000000000000000000009061314316565b63ffffffff166020556124ec565b506000611dd6565b8260098111156124f857fe5b604080516001600160a01b038516815290517f0e4f2c4b5bc209d509bc3d49348c787fefadc66a79351b470599ac0f5be52eaf9181900360200190a250600192915050565b60136020526000908152604090205460ff1681565b60196020526000908152604090205460ff1681565b7f00000000000000000000000072c232d56542ba082592dee7c77b1c6cfa758bcd81565b601e6020526000908152604090205463ffffffff1681565b600080546001600160a01b031633146125f1576040805162461bcd60e51b81526020600482018190526024820152600080516020613561833981519152604482015290519081900360640190fd5b6001600160a01b038316612631576040805162461bcd60e51b8152602060048201526002602482015261494160f01b604482015290519081900360640190fd5b60008085600981111561264057fe5b141561270657612653600760068661319e565b156126d6576001600160a01b0384166000908152600760205260409020805463ffffffff19169055612686600585613297565b6126d657600580546001810182556000919091527f036b6384b5eca791c62761152d0c79bb0604c104a5fb6f4eb0703f3154bb3db00180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600660205260409020805460ff81161560ff199091168117909155612fa2565b600185600981111561271457fe5b14156127da57612727600a60098661319e565b156127aa576001600160a01b0384166000908152600a60205260409020805463ffffffff1916905561275a600885613297565b6127aa57600880546001810182556000919091527ff3f7a9fe364faab93b216da50a3214154f22a0a2b415b23a84c8169e8b636ee30180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600960205260409020805460ff81161560ff199091168117909155612fa2565b60028560098111156127e857fe5b141561293c576127fb600460038661319e565b15612894576001600160a01b0384166000908152600460205260409020805463ffffffff1916905561282e600285613297565b1580156128435750612841600b85613297565b155b1561289457600280546001810182556000919091527f405787fa12a823e0f2b7631cc41b3ba8828b3321ca811111fa75cd3aa3bb5ace0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b03831660009081526003602052604090205460ff16158015806128d857506001600160a01b0384166000908152600c602052604090205460ff16155b6129135760405162461bcd60e51b81526004018080602001828103825260218152602001806135816021913960400191505060405180910390fd5b6001600160a01b0384166000908152600360205260409020805460ff1916821515179055612fa2565b600385600981111561294a57fe5b1415612a4d5761295d601460138661319e565b15612a1d57601280546001810182557fbb8a6a4669ba250d26cd7a459eca9d215f8307e33aebe50379bc5a3617ec34440180546001600160a01b0319166001600160a01b0387169081179091556000908152601460205260409020805463ffffffff191690556129cd9085613297565b612a1d57601280546001810182556000919091527fbb8a6a4669ba250d26cd7a459eca9d215f8307e33aebe50379bc5a3617ec34440180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601360205260409020805460ff81161560ff199091168117909155612fa2565b6004856009811115612a5b57fe5b1415612b5e57612a6e6010600f8661319e565b15612b2e57600e80546001810182557fbb7b4a454dc3493923482f07822329ed19e8244eff582cc204f8554c3620c3fd0180546001600160a01b0319166001600160a01b0387169081179091556000908152601060205260409020805463ffffffff19169055612ade9085613297565b612b2e57600e80546001810182556000919091527fbb7b4a454dc3493923482f07822329ed19e8244eff582cc204f8554c3620c3fd0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600f60205260409020805460ff81161560ff199091168117909155612fa2565b6005856009811115612b6c57fe5b1415612ce057612b7f600d600c8661319e565b15612c18576001600160a01b0384166000908152600d60205260409020805463ffffffff19169055612bb2600b85613297565b158015612bc75750612bc5600285613297565b155b15612c1857600b80546001810182556000919091527f0175b7a638427703f0dbe7bb9bbf987a2551717b34e79f33b5b1008d1fa01db90180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152600c602052604090205460ff1615801580612c5c57506001600160a01b03841660009081526003602052604090205460ff16155b612c975760405162461bcd60e51b81526004018080602001828103825260218152602001806135816021913960400191505060405180910390fd5b6001600160a01b038481166000908152600c60209081526040808320805460ff19168615151790556011909152902080546001600160a01b031916918516919091179055612fa2565b6006856009811115612cee57fe5b1415612db457612d01601760168661319e565b15612d84576001600160a01b0384166000908152601760205260409020805463ffffffff19169055612d34601585613297565b612d8457601580546001810182556000919091527f55f448fdea98c4d29eb340757ef0a66cd03dbb9538908a6a81d96026b71ec4750180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601660205260409020805460ff81161560ff199091168117909155612fa2565b6007856009811115612dc257fe5b1415612e8857612dd5601a60198661319e565b15612e58576001600160a01b0384166000908152601a60205260409020805463ffffffff19169055612e08601885613297565b612e5857601880546001810182556000919091527fb13d2d76d1f4b7be834882e410b3e3a8afaf69f83600ae24db354391d2378d2e0180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601960205260409020805460ff81161560ff199091168117909155612fa2565b6008856009811115612e9657fe5b1415612f5c57612ea9601e601d8661319e565b15612f2c576001600160a01b0384166000908152601e60205260409020805463ffffffff19169055612edc601c85613297565b612f2c57601c80546001810182556000919091527f0e4562a10381dec21b205ed72637e6b1b523bdd0e4d4d50af5cd23dd4500a2110180546001600160a01b0319166001600160a01b0386161790555b506001600160a01b0383166000908152601d60205260409020805460ff81161560ff199091168117909155612fa2565b6009856009811115612f6a57fe5b1415612f9857506000602055601f80546001600160a01b0319166001600160a01b0385161790556001612fa2565b6000915050612ff9565b846009811115612fae57fe5b604080516001600160a01b0387168152831515602082015281517f0dcacb7e392f3d6a216ed2660e3dcfd40b7793d33591db2ba185a6b8e44fc477929181900390910190a260019150505b9392505050565b60225481565b600b8181548110610b7c57600080fd5b60106020526000908152604090205463ffffffff1681565b80820382811115611dd657600080fd5b604080516001600160a01b038416602482015260448082018490528251808303909101815260649091019091526020810180516001600160e01b031663a9059cbb60e01b179052610cc79084906132e7565b80820182811015611dd657600080fd5b604080516001600160a01b0380861660248301528416604482015260648082018490528251808303909101815260849091019091526020810180516001600160e01b03166323b872dd60e01b1790526130fa9085906132e7565b50505050565b600082158061311b5750508181028183828161311857fe5b04145b611dd657600080fd5b600080821161313257600080fd5b81838161313b57fe5b049392505050565b80820163ffffffff8084169082161015611dd657600080fd5b600063ffffffff8316158061311b57508163ffffffff168363ffffffff1683850292508263ffffffff168161318d57fe5b0463ffffffff1614611dd657600080fd5b6001600160a01b03811660009081526020839052604081205460ff1661328d576001600160a01b03821660009081526020859052604090205463ffffffff1661321b576040805162461bcd60e51b815260206004820152600a6024820152694d75737420717565756560b01b604482015290519081900360640190fd5b6001600160a01b03821660009081526020859052604090205463ffffffff42811691161115613285576040805162461bcd60e51b8152602060048201526011602482015270145d595d59481b9bdd08195e1c1a5c9959607a1b604482015290519081900360640190fd5b506001612ff9565b5060009392505050565b6000805b835481101561328d57826001600160a01b03168482815481106132ba57fe5b6000918252602090912001546001600160a01b031614156132df576001915050611dd6565b60010161329b565b606061333c826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b03166133989092919063ffffffff16565b805190915015610cc75780806020019051602081101561335b57600080fd5b5051610cc75760405162461bcd60e51b815260040180806020018281038252602a8152602001806135c2602a913960400191505060405180910390fd5b60606133a784846000856133af565b949350505050565b60606133ba8561355a565b61340b576040805162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e7472616374000000604482015290519081900360640190fd5b60006060866001600160a01b031685876040518082805190602001908083835b6020831061344a5780518252601f19909201916020918201910161342b565b6001836020036101000a03801982511681845116808217855250505050505090500191505060006040518083038185875af1925050503d80600081146134ac576040519150601f19603f3d011682016040523d82523d6000602084013e6134b1565b606091505b509150915081156134c55791506133a79050565b8051156134d55780518082602001fd5b8360405162461bcd60e51b81526004018080602001828103825283818151815260200191508051906020019080838360005b8381101561351f578181015183820152602001613507565b50505050905090810190601f16801561354c5780820380516001836020036101000a031916815260200191505b509250505060405180910390fd5b3b15159056fe4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572446f206e6f742061646420746f20626f7468207479706573206f6620746f6b656e93bb8edd35984706eee1b92541281f7f62d33c01c5b2ec0929a113603bd21d665361666545524332303a204552433230206f7065726174696f6e20646964206e6f742073756363656564a2646970667358221220bf3fa5833ad71910cd248eb0ee8de8969806bdd8f418ccddf1fd080c8a0d16c064736f6c63430007050033