false
true
0

Contract Address Details

0x5a24D7129B6f3FcAd2220296df28911880AD22B0

Token
PLSZEN (PZEN)
Creator
0x33d52a–2dbb40 at 0x6381e9–9ab379
Balance
0.01 PLS ( )
Tokens
Fetching tokens...
Transactions
4,383 Transactions
Transfers
0 Transfers
Gas Used
0
Last Balance Update
26049049
Warning! Contract bytecode has been changed and doesn't match the verified one. Therefore, interaction with this smart contract may be risky.
Contract name:
PZENDEPLOYERcontract




Optimization enabled
false
Compiler version
v0.8.4+commit.c7e474f2




EVM Version
default




Verified at
2024-02-12T06:20:48.740639Z

Contract source code

/**
 *Submitted for verification at Etherscan.io on 2022-08-08
*/

/**
 * author: pif
 *
 *
 * maxfee9 v1.08 beta
 *
 * This is a rewrite of maxfee in the hope to:
 * - create the Socially engineeered token
 * - make it easier to change the tokenomics
 * - make it easier to maintain the code and develop it further
 * - remove redundant code
 * - fix some of the issues reported in the audit (e.g. SSL-03)
 *      
 *
 *
 *copyright all rights reserved
 * SPDX-License-Identifier: MIT
 */
pragma solidity ^0.8.4;

/**
 * Tokenomics:
 * 
 * Liquidity        0%
 * Redistribution   2%
 * Burn             0.1%
 * Charity          0.2%
 * Marketing        0%
  */

interface IERC20 {
    function totalSupply() external view returns (uint256);
    function balanceOf(address account) external view returns (uint256);
    function transfer(address recipient, uint256 amount) external returns (bool);
    function allowance(address owner, address spender) external view returns (uint256);
    function approve(address spender, uint256 amount) external returns (bool);
    function transferFrom(address sender, address recipient, uint256 amount) external returns (bool);
    event Transfer(address indexed from, address indexed to, uint256 value);
    event Approval(address indexed owner, address indexed spender, uint256 value);
}
interface IERC20Metadata is IERC20 {
    function name() external view returns (string memory);
    function symbol() external view returns (string memory);
    function decimals() external view returns (uint8);
}
abstract contract Context {
    function _msgSender() internal view virtual returns (address) {return msg.sender;}
    function _msgData() internal view virtual returns (bytes calldata) {this; return msg.data;}
}
library SafeMath {
    function add(uint256 a, uint256 b) internal pure returns (uint256) {return a + b;}
    function sub(uint256 a, uint256 b) internal pure returns (uint256) {return a - b;}
    function mul(uint256 a, uint256 b) internal pure returns (uint256) {return a * b;}
    function div(uint256 a, uint256 b) internal pure returns (uint256) {return a / b;}
    function mod(uint256 a, uint256 b) internal pure returns (uint256) {return a % b;}
    function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
        unchecked { require(b <= a, errorMessage); return a - b; }
    }
}
library Address {
    function isContract(address account) internal view returns (bool) { uint256 size; assembly { size := extcodesize(account) } return size > 0;}
    function sendValue(address payable recipient, uint256 amount) internal {
        require(address(this).balance >= amount, "Address: insufficient balance");(bool success, ) = recipient.call{ value: amount }("");
        require(success, "Address: unable to send value, recipient may have reverted");
    }
    function functionCall(address target, bytes memory data) internal returns (bytes memory) {return functionCall(target, data, "Address: low-level call failed");}
    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 value) internal returns (bytes memory) {return functionCallWithValue(target, data, value, "Address: low-level call with value failed");}
    function functionCallWithValue(address target, bytes memory data, uint256 value, string memory errorMessage) internal returns (bytes memory) {
        require(address(this).balance >= value, "Address: insufficient balance for call");
        require(isContract(target), "Address: call to non-contract");
        (bool success, bytes memory returndata) = target.call{ value: value }(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }
    function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
        return functionStaticCall(target, data, "Address: low-level static call failed");
    }
    function functionStaticCall(address target, bytes memory data, string memory errorMessage) internal view returns (bytes memory) {
        require(isContract(target), "Address: static call to non-contract");
        (bool success, bytes memory returndata) = target.staticcall(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }
    function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
        return functionDelegateCall(target, data, "Address: low-level delegate call failed");
    }
    function functionDelegateCall(address target, bytes memory data, string memory errorMessage) internal returns (bytes memory) {
        require(isContract(target), "Address: delegate call to non-contract");
        (bool success, bytes memory returndata) = target.delegatecall(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }
    function _verifyCallResult(bool success, bytes memory returndata, string memory errorMessage) private pure returns(bytes memory) {
        if (success) { return returndata; } else {
            if (returndata.length > 0) {
                assembly {
                    let returndata_size := mload(returndata)
                    revert(add(32, returndata), returndata_size)
                }
            } else {revert(errorMessage);}
        }
    }
}
abstract contract Ownable is Context {
    address private _owner;
    address private _previousOwner;
    uint256 private _lockTime;
    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
    constructor () {
        address msgSender = _msgSender();
        _owner = msgSender;
        emit OwnershipTransferred(address(0), msgSender);
    }
    function owner() public view returns (address) {
        return _owner;
    }
    modifier onlyOwner() {
        require(_owner == _msgSender(), "Ownable: caller is not the owner");
        _;
    }
    function renounceOwnership() public virtual onlyOwner {
        emit OwnershipTransferred(_owner, address(0));
        _owner = address(0);
    }
    function transferOwnership(address newOwner) public virtual onlyOwner {
        require(newOwner != address(0), "Ownable: new owner is the zero address");
        emit OwnershipTransferred(_owner, newOwner);
        _owner = newOwner;
    }
    function getUnlockTime() public view returns (uint256) {
        return _lockTime;
    }
    function lock(uint256 time) public virtual onlyOwner {
        _previousOwner = _owner;
        _owner = address(0);
        _lockTime = block.timestamp + time;
        emit OwnershipTransferred(_owner, address(0));
    }
    function unlock() public virtual {
        require(_previousOwner == msg.sender, "Only the previous owner can unlock onwership");
        require(block.timestamp > _lockTime , "The contract is still locked");
        emit OwnershipTransferred(_owner, _previousOwner);
        _owner = _previousOwner;
    }
}
abstract contract Manageable is Context {
    address private _manager;
    event ManagementTransferred(address indexed previousManager, address indexed newManager);
    constructor(){
        address msgSender = _msgSender();
        _manager = msgSender;
        emit ManagementTransferred(address(0), msgSender);
    }
    function manager() public view returns(address){ return _manager; }
    modifier onlyManager(){
        require(_manager == _msgSender(), "Manageable: caller is not the manager");
        _;
    }
    function transferManagement(address newManager) external virtual onlyManager {
        emit ManagementTransferred(_manager, newManager);
        _manager = newManager;
    }
}
interface IPancakeV2Factory {
    event PairCreated(address indexed token0, address indexed token1, address pair, uint);
    function createPair(address tokenA, address tokenB) external returns (address pair);
}
interface IPancakeV2Router {
    function factory() external pure returns (address);
    function WETH() external pure returns (address);
    function addLiquidityETH(
        address token,
        uint amountTokenDesired,
        uint amountTokenMin,
        uint amountETHMin,
        address to,
        uint deadline
    ) external payable returns (uint amountToken, uint amountETH, uint liquidity);
    function swapExactTokensForETHSupportingFeeOnTransferTokens(
        uint amountIn,
        uint amountOutMin,
        address[] calldata path,
        address to,
        uint deadline
    ) external;
}

/**
 * BULL
 * 
 * You can add  if you want. 
  * NOTE: the PFI fee. 
 * you should be using this contract at all (you're just wasting gas if you do).
 *
 * - extra fee (e.g. double) over a threshold 
 */
abstract contract Tokenomics {
    
    using SafeMath for uint256;
    
    // --------------------- Token Settings ------------------- //

    string internal constant NAME = "PLSZEN";
    string internal constant SYMBOL = "PZEN";
    
    uint16 internal constant FEES_DIVISOR = 10**4;
    uint8 internal constant DECIMALS = 9;
    uint256 internal constant ZEROES = 10**DECIMALS;
    
    uint256 private constant MAX = ~uint256(0);
    uint256 internal constant TOTAL_SUPPLY = 880 * 10**6 *10**9;
    uint256 internal _reflectedSupply = (MAX - (MAX % TOTAL_SUPPLY));

    /**
     * @dev Set the maximum transaction amount allowed in a transfer.
     * 
     * The default value is 1% of the total supply. 
     * 
     * NOTE: set the value to `TOTAL_SUPPLY` to have an unlimited max, i.e.
     * `maxTransactionAmount = TOTAL_SUPPLY;`
     */
    uint256 internal constant maxTransactionAmount = TOTAL_SUPPLY;
    
    /**
     * @dev Set the maximum allowed balance in a wallet.
     * 
     * The default value is 2% of the total supply. 
     * 
     * NOTE: set the value to 0 to have an unlimited max.
     *
     * IMPORTANT: This value MUST be greater than `numberOfTokensToSwapToLiquidity` set below,
     * otherwise the liquidity swap will never be executed
     */
    uint256 internal constant maxWalletBalance = TOTAL_SUPPLY / 3; // 2% of the total supply
    
    /**
     * @dev Set the number of tokens to swap and add to liquidity. 
     * 
     * Whenever the contract's balance reaches this number of tokens, swap & liquify will be 
     * executed in the very next transfer (via the `_beforeTokenTransfer`)
     * 
     * If the `FeeType.Liquidity` is enabled in `FeesSettings`, the given % of each transaction will be first
     * sent to the contract address. Once the contract's balance reaches `numberOfTokensToSwapToLiquidity` the
     * `swapAndLiquify` of `Liquifier` will be executed. Half of the tokens will be swapped for ETH 
     * (or BNB on BSC) and together with the other half converted into a Token-ETH/Token-BNB LP Token.
     * 
     * See: `Liquifier`
     */
    uint256 internal constant numberOfTokensToSwapToLiquidity = TOTAL_SUPPLY / 1000; // 0.1% of the total supply

    // --------------------- Fees Settings ------------------- //

    /**
     * @dev To add/edit/remove fees scroll down to the `addFees` function below
     */

    address internal charityAddress = 0xe83b3c8fc65f6DacfCcC90C8cAc45a1f1dD38a2d;
    address internal marketingAddress = 0xe83b3c8fc65f6DacfCcC90C8cAc45a1f1dD38a2d;

    /**
     * @dev You can change the value of the burn address to pretty much anything
     * that's (clearly) a non-random address, i.e. for which the probability of 
     * someone having the private key is (virtually) 0. For example, 0x00.....1, 
     * 0x111...111, 0x12345.....12345, etc.
     *
     * NOTE: This does NOT need to be the zero address, adress(0) = 0x000...000;
     *
     * Trasfering tokens to the burn address is good for DEFLATION. Nevertheless
     * if the burn address is excluded from rewards, sending tokens
     * to the burn address actually improves redistribution to holders (as they will
     * have a larger % of tokens in non-excluded accounts)
     *
     * p.s. the address below is the speed of light in vacuum in m/s (expressed in decimals),
     * the hex value is 0x0000000000000000000000000000000011dE784A; :)
     *
     * Here are the values of some other fundamental constants to use:
     * 0x0000000000000000000000000000000602214076 (Avogardo constant)
     * 0x0000000000000000000000000000000001380649 (Boltzmann constant)
     * 0x2718281828459045235360287471352662497757 (e)
     * 0x0000000000000000000000000000001602176634 (elementary charge)
     * 0x0000000000000000000000000200231930436256 (electron g-factor)
     * 0x0000000000000000000000000000091093837015 (electron mass)
     * 0x0000000000000000000000000000137035999084 (fine structure constant)
     * 0x0577215664901532860606512090082402431042 (Euler-Mascheroni constant)
     * 0x1618033988749894848204586834365638117720 (golden ratio)
     * 0x0000000000000000000000000000009192631770 (hyperfine transition fq)
     * 0x0000000000000000000000000000010011659208 (muom g-2)
     * 0x3141592653589793238462643383279502884197 (pi)
     * 0x0000000000000000000000000000000662607015 (Planck's constant)
     * 0x0000000000000000000000000000001054571817 (reduced Planck's constant)
     * 0x1414213562373095048801688724209698078569 (sqrt(2))
     */
    address internal burnAddress = 0x1414213562373095048801688724209698078569 ;

    /**
     * @dev You 
     * rewriting PZEN
     *
     * keep this
     * and you'll be added to the partners section to promote your token. 
     */
    address internal tipToTheDev = 0x079086722C172eb0aDC9886529D2b8139Bc45667;

    enum FeeType { Antiwhale, Burn, Liquidity, Rfi, External, ExternalToETH }
    struct Fee {
        FeeType name;
        uint256 value;
        address recipient;
        uint256 total;
    }

    Fee[] internal fees;
    uint256 internal sumOfFees;

    constructor() {
        _addFees();
    }

    function _addFee(FeeType name, uint256 value, address recipient) private {
        fees.push( Fee(name, value, recipient, 0 ) );
        sumOfFees += value;
    }

    function _addFees() private {

        /**
         * The PFI recipient is ignored but we need to give a valid address value
         *
         * CAUTION:
         *      There are more efficient and cleaner token contracts without PFI 
         *      so you should use one of those
         *
         * The value of fees is given 
         * e.g. for 5% use 
         */ 
        _addFee(FeeType.Rfi, 200, address(this) ); 

        _addFee(FeeType.Burn, 1, burnAddress );
        _addFee(FeeType.Liquidity, 0, address(this) );
        _addFee(FeeType.External, 20, charityAddress );
        _addFee(FeeType.External, 0, marketingAddress );

        // 0.1% as a tip removed
       // _addFee(FeeType.ExternalToETH, 1, tipToTheDev );
    }

    function _getFeesCount() internal view returns (uint256){ return fees.length; }

    function _getFeeStruct(uint256 index) private view returns(Fee storage){
        require( index >= 0 && index < fees.length, "FeesSettings._getFeeStruct: Fee index out of bounds");
        return fees[index];
    }
    function _getFee(uint256 index) internal view returns (FeeType, uint256, address, uint256){
        Fee memory fee = _getFeeStruct(index);
        return ( fee.name, fee.value, fee.recipient, fee.total );
    }
    function _addFeeCollectedAmount(uint256 index, uint256 amount) internal {
        Fee storage fee = _getFeeStruct(index);
        fee.total = fee.total.add(amount);
    }

    // function getCollectedFeeTotal(uint256 index) external view returns (uint256){
    function getCollectedFeeTotal(uint256 index) internal view returns (uint256){
        Fee memory fee = _getFeeStruct(index);
        return fee.total;
    }
}

abstract contract Presaleable is Manageable {
    bool internal isInPresale;
    function setPreseableEnabled(bool value) external onlyManager {
        isInPresale = value;
    }
}

abstract contract BaseRfiToken is IERC20, IERC20Metadata, Ownable, Presaleable, Tokenomics {

    using SafeMath for uint256;
    using Address for address;

    mapping (address => uint256) internal _reflectedBalances;
    mapping (address => uint256) internal _balances;
    mapping (address => mapping (address => uint256)) internal _allowances;
    
    mapping (address => bool) internal _isExcludedFromFee;
    mapping (address => bool) internal _isExcludedFromRewards;
    address[] private _excluded;
    
    constructor(){
        
        _reflectedBalances[owner()] = _reflectedSupply;
        
        // exclude owner and this contract from fee
        _isExcludedFromFee[owner()] = true;
        _isExcludedFromFee[address(this)] = true;
        
        // exclude the owner and this contract from rewards
        _exclude(owner());
        _exclude(address(this));

        emit Transfer(address(0), owner(), TOTAL_SUPPLY);
        
    }
    
    /** Functions required by IERC20Metadat **/
        function name() external pure override returns (string memory) { return NAME; }
        function symbol() external pure override returns (string memory) { return SYMBOL; }
        function decimals() external pure override returns (uint8) { return DECIMALS; }
        
    /** Functions required by IERC20Metadat - END **/
    /** Functions required by IERC20 **/
        function totalSupply() external pure override returns (uint256) {
            return TOTAL_SUPPLY;
        }
        
        function balanceOf(address account) public view override returns (uint256){
            if (_isExcludedFromRewards[account]) return _balances[account];
            return tokenFromReflection(_reflectedBalances[account]);
        }
        
        function transfer(address recipient, uint256 amount) external override returns (bool){
            _transfer(_msgSender(), recipient, amount);
            return true;
        }
        
        function allowance(address owner, address spender) external view override returns (uint256){
            return _allowances[owner][spender];
        }
    
        function approve(address spender, uint256 amount) external override returns (bool) {
            _approve(_msgSender(), spender, amount);
            return true;
        }
        
        function transferFrom(address sender, address recipient, uint256 amount) external override returns (bool){
            _transfer(sender, recipient, amount);
            _approve(sender, _msgSender(), _allowances[sender][_msgSender()].sub(amount, "ERC20: transfer amount exceeds allowance"));
            return true;
        }
    /** Functions required by IERC20 - END **/

    /**
     * @dev this is really a "soft" burn (total supply is not reduced). PFI holders
     * get two benefits from burning tokens:
     *
     * 1) Tokens in the burn address increase the % of tokens held by holders not
     *    excluded from rewards (assuming the burn address is excluded)
     * 2) Tokens in the burn address cannot be sold (which in turn draing the 
     *    liquidity pool)
     *
     *
     * In PFI holders already get % of each transaction so the value of their tokens 
     * increases (in a way). Therefore there is really no need to do a "hard" burn 
     * (reduce the total supply). What matters (in PFI) is to make sure that a large
     * amount of tokens cannot be sold = draining the liquidity pool = lowering the
     * value of tokens holders own. For this purpose, transfering tokens to a (vanity)
     * burn address is the most appropriate way to "burn". 
     *
     * There is an extra check placed into the `transfer` function to make sure the
     * burn address cannot withdraw the tokens is has
     * virtually zero).
     */
    function burn(uint256 amount) external {

        address sender = _msgSender();
        require(sender != address(0), "BaseRfiToken: burn from the zero address");
        require(sender != address(burnAddress), "BaseRfiToken: burn from the burn address");

        uint256 balance = balanceOf(sender);
        require(balance >= amount, "BaseRfiToken: burn amount exceeds balance");

        uint256 reflectedAmount = amount.mul(_getCurrentRate());

        // remove the amount from the sender's balance first
        _reflectedBalances[sender] = _reflectedBalances[sender].sub(reflectedAmount);
        if (_isExcludedFromRewards[sender])
            _balances[sender] = _balances[sender].sub(amount);

        _burnTokens( sender, amount, reflectedAmount );
    }
    
    /**
     * @dev  burns the specified amount of tokens by sending them 
     * to the burn address
     */
    function _burnTokens(address sender, uint256 tBurn, uint256 rBurn) internal {

        /**
         * @dev Do not reduce (soft) burning by sending
         * tokens to the burn address (which should be excluded from rewards) is sufficient
         * in PFI
         */ 
        _reflectedBalances[burnAddress] = _reflectedBalances[burnAddress].add(rBurn);
        if (_isExcludedFromRewards[burnAddress])
            _balances[burnAddress] = _balances[burnAddress].add(tBurn);

        /**
         * @dev Emit the event so that the burn address balance is updated (on bscscan)
         */
        emit Transfer(sender, burnAddress, tBurn);
    }

    function increaseAllowance(address spender, uint256 addedValue) public virtual returns (bool) {
        _approve(_msgSender(), spender, _allowances[_msgSender()][spender].add(addedValue));
        return true;
    }
    
    function decreaseAllowance(address spender, uint256 subtractedValue) public virtual returns (bool) {
        _approve(_msgSender(), spender, _allowances[_msgSender()][spender].sub(subtractedValue, "ERC20: decreased allowance below zero"));
        return true;
    }
    
    function isExcludedFromReward(address account) external view returns (bool) {
        return _isExcludedFromRewards[account];
    }

    /**
     * @dev Calculates and returns the reflected amount for the given amount with or without 
     * the transfer fees (deductTransferFee true/false)
     */
    function reflectionFromToken(uint256 tAmount, bool deductTransferFee) external view returns(uint256) {
        require(tAmount <= TOTAL_SUPPLY, "Amount must be less than supply");
        if (!deductTransferFee) {
            (uint256 rAmount,,,,) = _getValues(tAmount,0);
            return rAmount;
        } else {
            (,uint256 rTransferAmount,,,) = _getValues(tAmount,_getSumOfFees(_msgSender(), tAmount));
            return rTransferAmount;
        }
    }

    /**
     * @dev Calculates and returns the amount of tokens corresponding to the given reflected amount.
     */
    function tokenFromReflection(uint256 rAmount) internal view returns(uint256) {
        require(rAmount <= _reflectedSupply, "Amount must be less than total reflections");
        uint256 currentRate = _getCurrentRate();
        return rAmount.div(currentRate);
    }
    
    function excludeFromReward(address account) external onlyOwner() {
        require(!_isExcludedFromRewards[account], "Account is not included");
        _exclude(account);
    }
    
    function _exclude(address account) internal {
        if(_reflectedBalances[account] > 0) {
            _balances[account] = tokenFromReflection(_reflectedBalances[account]);
        }
        _isExcludedFromRewards[account] = true;
        _excluded.push(account);
    }

    function includeInReward(address account) external onlyOwner() {
        require(_isExcludedFromRewards[account], "Account is not excluded");
        for (uint256 i = 0; i < _excluded.length; i++) {
            if (_excluded[i] == account) {
                _excluded[i] = _excluded[_excluded.length - 1];
                _balances[account] = 0;
                _isExcludedFromRewards[account] = false;
                _excluded.pop();
                break;
            }
        }
    }
    
    function setExcludedFromFee(address account, bool value) external onlyOwner { _isExcludedFromFee[account] = value; }
    function isExcludedFromFee(address account) public view returns(bool) { return _isExcludedFromFee[account]; }
    
    function _approve(address owner, address spender, uint256 amount) internal {
        require(owner != address(0), "BaseRfiToken: approve from the zero address");
        require(spender != address(0), "BaseRfiToken: approve to the zero address");

        _allowances[owner][spender] = amount;
        emit Approval(owner, spender, amount);
    }
    
    /**
     */
    function _isUnlimitedSender(address account) internal view returns(bool){
        // the owner should be the only whitelisted sender
        return (account == owner());
    }
    /**
     */
    function _isUnlimitedRecipient(address account) internal view returns(bool){
        // the owner should be a white-listed recipient
        // and anyone should be able to burn as many tokens as 
        // he/she wants
        return (account == owner() || account == burnAddress);
    }

    function _transfer(address sender, address recipient, uint256 amount) private {
        require(sender != address(0), "BaseRfiToken: transfer from the zero address");
        require(recipient != address(0), "BaseRfiToken: transfer to the zero address");
        require(sender != address(burnAddress), "BaseRfiToken: transfer from the burn address");
        require(amount > 0, "Transfer amount must be greater than zero");
        
        // indicates whether or not feee should be deducted from the transfer
        bool takeFee = true;

        if ( isInPresale ){ takeFee = false; }
        else {
            /**
            * Check the amount is within the max allowed limit as long as a
            * unlimited sender/recepient is not involved in the transaction
            */
            if ( amount > maxTransactionAmount && !_isUnlimitedSender(sender) && !_isUnlimitedRecipient(recipient) ){
                revert("Transfer amount exceeds the maxTxAmount.");
            }
            /**
            * The pair needs to excluded from the max wallet balance check; 
            * selling tokens is sending them back to the pair (without this
            * check, selling tokens would not work if the pair's balance 
            * was over the allowed max)
            *
            * Note: This does NOT take into account the fees which will be deducted 
            *       from the amount. As such it could be a bit confusing 
            */
            if ( maxWalletBalance > 0 && !_isUnlimitedSender(sender) && !_isUnlimitedRecipient(recipient) && !_isV2Pair(recipient) ){
                uint256 recipientBalance = balanceOf(recipient);
                require(recipientBalance + amount <= maxWalletBalance, "New balance would exceed the maxWalletBalance");
            }
        }

        // if any account belongs to _isExcludedFromFee account then remove the fee
        if(_isExcludedFromFee[sender] || _isExcludedFromFee[recipient]){ takeFee = false; }

        _beforeTokenTransfer(sender, recipient, amount, takeFee);
        _transferTokens(sender, recipient, amount, takeFee);
        
    }

    function _transferTokens(address sender, address recipient, uint256 amount, bool takeFee) private {
    
        /**
         * We don't need to know anything about the individual fees here 
         * (like max does with `_getValues`). All that is required 
         * for the transfer is the sum of all fees to calculate the % of the total 
         * transaction amount which should be transferred to the recipient. 
         *
         * The `_takeFees` call will/should take care of the individual fees
         */
        uint256 sumOfFees = _getSumOfFees(sender, amount);
        if ( !takeFee ){ sumOfFees = 0; }
        
        (uint256 rAmount, uint256 rTransferAmount, uint256 tAmount, uint256 tTransferAmount, uint256 currentRate ) = _getValues(amount, sumOfFees);
        
        /** 
         * Sender's and Recipient's reflected balances must be always updated regardless of
         * whether they are excluded from rewards or not.
         */ 
        _reflectedBalances[sender] = _reflectedBalances[sender].sub(rAmount);
        _reflectedBalances[recipient] = _reflectedBalances[recipient].add(rTransferAmount);

        /**
         * Update the true/nominal balances for excluded accounts
         */        
        if (_isExcludedFromRewards[sender]){ _balances[sender] = _balances[sender].sub(tAmount); }
        if (_isExcludedFromRewards[recipient] ){ _balances[recipient] = _balances[recipient].add(tTransferAmount); }
        
        _takeFees( amount, currentRate, sumOfFees );
        emit Transfer(sender, recipient, tTransferAmount);
    }
    
    function _takeFees(uint256 amount, uint256 currentRate, uint256 sumOfFees ) private {
        if ( sumOfFees > 0 && !isInPresale ){
            _takeTransactionFees(amount, currentRate);
        }
    }
    
    function _getValues(uint256 tAmount, uint256 feesSum) internal view returns (uint256, uint256, uint256, uint256, uint256) {
        
        uint256 tTotalFees = tAmount.mul(feesSum).div(FEES_DIVISOR);
        uint256 tTransferAmount = tAmount.sub(tTotalFees);
        uint256 currentRate = _getCurrentRate();
        uint256 rAmount = tAmount.mul(currentRate);
        uint256 rTotalFees = tTotalFees.mul(currentRate);
        uint256 rTransferAmount = rAmount.sub(rTotalFees);
        
        return (rAmount, rTransferAmount, tAmount, tTransferAmount, currentRate);
    }
    
    function _getCurrentRate() internal view returns(uint256) {
        (uint256 rSupply, uint256 tSupply) = _getCurrentSupply();
        return rSupply.div(tSupply);
    }
    
    function _getCurrentSupply() internal view returns(uint256, uint256) {
        uint256 rSupply = _reflectedSupply;
        uint256 tSupply = TOTAL_SUPPLY;  

        /**
         * The code below removes balances of addresses excluded from rewards from
         * rSupply and tSupply, which effectively increases the % of transaction fees
         * delivered to non-excluded holders
         */    
        for (uint256 i = 0; i < _excluded.length; i++) {
            if (_reflectedBalances[_excluded[i]] > rSupply || _balances[_excluded[i]] > tSupply) return (_reflectedSupply, TOTAL_SUPPLY);
            rSupply = rSupply.sub(_reflectedBalances[_excluded[i]]);
            tSupply = tSupply.sub(_balances[_excluded[i]]);
        }
        if (tSupply == 0 || rSupply < _reflectedSupply.div(TOTAL_SUPPLY)) return (_reflectedSupply, TOTAL_SUPPLY);
        return (rSupply, tSupply);
    }
    
    /**
     * @dev Hook that is called.
     */
    function _beforeTokenTransfer(address sender, address recipient, uint256 amount, bool takeFee) internal virtual;
    
    /**
     * @dev Returns. 
     * 
     * To separate concerns this contract (class) will take care of ONLY handling PFI, i.e. 
     * changing the rates and updating the holder's balance (via `_redistribute`). 
     * It is not the responsibility of the dev/user to handle all other fees and taxes 
     * in the appropriate contracts (classes).
     */ 
    function _getSumOfFees(address sender, uint256 amount) internal view virtual returns (uint256);

    /**
     * @dev A delegate 
     */
    function _isV2Pair(address account) internal view virtual returns(bool);

    /**
     * @dev Redistributes the specified amount among the current holders via the reflect.finance
     * algorithm, which ultimately adjusts the
     * current rate used by  and, in turn, the value returns from `Of`. 
     * This is the bit of clever math which allows pfi to redistribute the fee without 
     * having to iterate through all holders. 
     */
    function _redistribute(uint256 amount, uint256 currentRate, uint256 fee, uint256 index) internal {
        uint256 tFee = amount.mul(fee).div(FEES_DIVISOR);
        uint256 rFee = tFee.mul(currentRate);

        _reflectedSupply = _reflectedSupply.sub(rFee);
        _addFeeCollectedAmount(index, tFee);
    }

    /**
     * @dev Hook that is called before event is emitted if fees are enabled for the transfer
     */
    function _takeTransactionFees(uint256 amount, uint256 currentRate) internal virtual;
}

abstract contract Liquifier is Ownable, Manageable {

    using SafeMath for uint256;

    uint256 private withdrawableBalance;

    enum Env {Testnet, MainnetV1, MainnetV2}
    Env private _env;

    // PancakeSwap V1
    address private _mainnetRouterV1Address = 0x05fF2B0DB69458A0750badebc4f9e13aDd608C7F;
    // PancakeSwap V2
    address private _mainnetRouterV2Address = 0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D;
    // Testnet
    // address private _testnetRouterAddress = 0xD99D1c33F9fC3444f8101754aBC46c52416550D1;
    // PancakeSwap Testnet = https://pancake.kiemtienonline360.com/
    address private _testnetRouterAddress = 0x7a250d5630B4cF539739dF2C5dAcb4c659F2488D;

    IPancakeV2Router internal _router;
    address internal _pair;
    
    bool private inSwapAndLiquify;
    bool private swapAndLiquifyEnabled = true;

    uint256 private maxTransactionAmount;
    uint256 private numberOfTokensToSwapToLiquidity;

    modifier lockTheSwap {
        inSwapAndLiquify = true;
        _;
        inSwapAndLiquify = false;
    }

    event RouterSet(address indexed router);
    event SwapAndLiquify(uint256 tokensSwapped, uint256 ethReceived, uint256 tokensIntoLiquidity);
    event SwapAndLiquifyEnabledUpdated(bool enabled);
    event LiquidityAdded(uint256 tokenAmountSent, uint256 ethAmountSent, uint256 liquidity);

    receive() external payable {}

    function initializeLiquiditySwapper(Env env, uint256 maxTx, uint256 liquifyAmount) internal {
        _env = env;
        if (_env == Env.MainnetV1){ _setRouterAddress(_mainnetRouterV1Address); }
        else if (_env == Env.MainnetV2){ _setRouterAddress(_mainnetRouterV2Address); }
        else /*(_env == Env.Testnet)*/{ _setRouterAddress(_testnetRouterAddress); }

        maxTransactionAmount = maxTx;
        numberOfTokensToSwapToLiquidity = liquifyAmount;

    }

    /**
     * NOTE: passing the `contractTokenBalance` here is preferred to creating `balanceOfDelegate`
     */
    function liquify(uint256 contractTokenBalance, address sender) internal {

        if (contractTokenBalance >= maxTransactionAmount) contractTokenBalance = maxTransactionAmount;
        
        bool isOverRequiredTokenBalance = ( contractTokenBalance >= numberOfTokensToSwapToLiquidity );
        
        /**
         * - first check if the contract has collected enough tokens to swap and liquify
         * - then check swap and liquify is enabled
         * - then make sure not to get caught in a circular liquidity event
         * - finally, don't swap & liquify if the sender is the uniswap pair
         */
        if ( isOverRequiredTokenBalance && swapAndLiquifyEnabled && !inSwapAndLiquify && (sender != _pair) ){
            // TODO check if the `(sender != _pair)` is necessary because that basically
            // stops swap and liquify for all "buy" transactions
            _swapAndLiquify(contractTokenBalance);            
        }

    }

    /**
     * @dev sets the router address and created the router, factory pair to enable
     * swapping and liquifying (contract) tokens
     */
    function _setRouterAddress(address router) private {
        IPancakeV2Router _newPancakeRouter = IPancakeV2Router(router);
        _pair = IPancakeV2Factory(_newPancakeRouter.factory()).createPair(address(this), _newPancakeRouter.WETH());
        _router = _newPancakeRouter;
        emit RouterSet(router);
    }
    
    function _swapAndLiquify(uint256 amount) private lockTheSwap {
        
        // split the contract balance into halves
        uint256 half = amount.div(2);
        uint256 otherHalf = amount.sub(half);
        
        // capture the contract's current ETH balance.
        // this is so that we can capture exactly the amount of ETH that the
        // swap creates, and not make the liquidity event include any ETH that
        // has been manually sent to the contract
        uint256 initialBalance = address(this).balance;
        
        // swap tokens for ETH
        _swapTokensForEth(half); // <- this breaks the ETH -> HATE swap when swap+liquify is triggered

        // how much ETH did we just swap into?
        uint256 newBalance = address(this).balance.sub(initialBalance);

        // add liquidity to uniswap
        _addLiquidity(otherHalf, newBalance);
        
        emit SwapAndLiquify(half, newBalance, otherHalf);
    }
    
    function _swapTokensForEth(uint256 tokenAmount) private {
        
        // generate the uniswap pair path of token -> weth
        address[] memory path = new address[](2);
        path[0] = address(this);
        path[1] = _router.WETH();

        _approveDelegate(address(this), address(_router), tokenAmount);

        // make the swap
        _router.swapExactTokensForETHSupportingFeeOnTransferTokens(
            tokenAmount,
            // The minimum amount of output tokens that must be received for the transaction not to revert.
            // 0 = accept any amount (slippage is inevitable)
            0,
            path,
            address(this),
            block.timestamp
        );
    }
    
    function _addLiquidity(uint256 tokenAmount, uint256 ethAmount) private {
        // approve token transfer to cover all possible scenarios
        _approveDelegate(address(this), address(_router), tokenAmount);

        // add tahe liquidity
        (uint256 tokenAmountSent, uint256 ethAmountSent, uint256 liquidity) = _router.addLiquidityETH{value: ethAmount}(
            address(this),
            tokenAmount,
            // Bounds the extent to which the WETH/token price can go up before the transaction reverts. 
            // Must be <= amountTokenDesired; 0 = accept any amount (slippage is inevitable)
            0,
            // Bounds the extent to which the token/WETH price can go up before the transaction reverts.
            // 0 = accept any amount (slippage is inevitable)
            0,
            // this is a centralized risk if the owner's account is ever compromised (see Certik SSL-04)
            owner(),
            block.timestamp
        );

        // fix the forever locked BNBs as per the noncertik's audit
        /**
         * The swapAndLiquify function converts half of the contractTokenBalance SafeMoon tokens to BNB. 
         * For every swapAndLiquify function call, a small amount of BNB remains in the contract. 
         * This amount grows over time with the swapAndLiquify function being called throughout the life 
         * of the contract. The Safemoon contract does not contain a method to withdraw these funds, 
         * and the BNB will be locked in the Safemoon contract forever.
         */
        withdrawableBalance = address(this).balance;
        emit LiquidityAdded(tokenAmountSent, ethAmountSent, liquidity);
    }
    

    /**
    * @dev Sets the uniswapV2 pair (router & factory) for swapping and liquifying tokens
    */
    function setRouterAddress(address router) external onlyManager() {
        _setRouterAddress(router);
    }

    /**
     * @dev Sends the swap and liquify flag to the provided value. If set to `false` tokens collected in the contract will
     * NOT be converted into liquidity.
     */
    function setSwapAndLiquifyEnabled(bool enabled) external onlyManager {
        swapAndLiquifyEnabled = enabled;
        emit SwapAndLiquifyEnabledUpdated(swapAndLiquifyEnabled);
    }

    /**
     * @dev The owner can withdraw ETH(BNB) collected in the contract from `pfiswapAndLiquify`
     * or if someone (accidentally) sends ETH/BNB directly to the contract.
     *
     * Note: This addresses the contract flaw 
     * 
     * The swapAndLiquify function converts 
     * For every swapAndLiquify function call, a small amount of BNB remains in the contract. 
     * This amount grows over time with the swapAndLiquify function being called 
     * throughout the life of the contract. 
     * to withdraw these funds, and the BNB will be locked in the contract forever.
     * https://www.certik.org/projects/
     */
    function withdrawLockedEth(address payable recipient) external onlyManager(){
        require(recipient != address(0), "Cannot withdraw the ETH balance to the zero address");
        require(withdrawableBalance > 0, "The ETH balance must be greater than 0");

        // prevent re-entrancy attacks
        uint256 amount = withdrawableBalance;
        withdrawableBalance = 0;
        recipient.transfer(amount);
    }

    /**
     * @dev Use this delegate instead of having (unnecessarily) extend `BasepfiToken` to gained access 
     * to the `_approve` function.
     */
    function _approveDelegate(address owner, address spender, uint256 amount) internal virtual;

}

//////////////////////////////////////////////////////////////////////////
abstract contract Antiwhale is Tokenomics {

    /**
     * @dev Returns the total sum of fees (in percents / per-mille - this depends on the FEES_DIVISOR value)
     *
     * NOTE: Currently this is just a placeholder. The parameters passed to this function are the
     *      sender's token balance and the transfer amount. An *antiwhale* mechanics can use these 
     *      values to adjust the fees total for each tx
     */
    // function _getAntiwhaleFees(uint256 sendersBalance, uint256 amount) internal view returns (uint256){
    function _getAntiwhaleFees(uint256, uint256) internal view returns (uint256){
        return sumOfFees;
    }
}
//////////////////////////////////////////////////////////////////////////

abstract contract PZEN is BaseRfiToken, Liquifier, Antiwhale {
    
    using SafeMath for uint256;

    // constructor(string memory _name, string memory _symbol, uint8 _decimals){
    constructor(Env _env){

        initializeLiquiditySwapper(_env, maxTransactionAmount, numberOfTokensToSwapToLiquidity);

        // exclude the pair address from rewards - we don't want to redistribute
        // tx fees to these two; redistribution is only for holders, dah!
        _exclude(_pair);
        _exclude(burnAddress);
    }
    
    function _isV2Pair(address account) internal view override returns(bool){
        return (account == _pair);
    }

    function _getSumOfFees(address sender, uint256 amount) internal view override returns (uint256){ 
        return _getAntiwhaleFees(balanceOf(sender), amount); 
    }
    
    // function _beforeTokenTransfer(address sender, address recipient, uint256 amount, bool takeFee) internal override {
    function _beforeTokenTransfer(address sender, address , uint256 , bool ) internal override {
        if ( !isInPresale ){
            uint256 contractTokenBalance = balanceOf(address(this));
            liquify( contractTokenBalance, sender );
        }
    }

    function _takeTransactionFees(uint256 amount, uint256 currentRate) internal override {
        
        if( isInPresale ){ return; }

        uint256 feesCount = _getFeesCount();
        for (uint256 index = 0; index < feesCount; index++ ){
            (FeeType name, uint256 value, address recipient,) = _getFee(index);
            // no need to check value < 0 as the value is uint (i.e. from 0 to 2^256-1)
            if ( value == 0 ) continue;

            if ( name == FeeType.Rfi ){
                _redistribute( amount, currentRate, value, index );
            }
            else if ( name == FeeType.Burn ){
                _burn( amount, currentRate, value, index );
            }
            else if ( name == FeeType.Antiwhale){
                // TODO
            }
            else if ( name == FeeType.ExternalToETH){
                _takeFeeToETH( amount, currentRate, value, recipient, index );
            }
            else {
                _takeFee( amount, currentRate, value, recipient, index );
            }
        }
    }

    function _burn(uint256 amount, uint256 currentRate, uint256 fee, uint256 index) private {
        uint256 tBurn = amount.mul(fee).div(FEES_DIVISOR);
        uint256 rBurn = tBurn.mul(currentRate);

        _burnTokens(address(this), tBurn, rBurn);
        _addFeeCollectedAmount(index, tBurn);
    }

    function _takeFee(uint256 amount, uint256 currentRate, uint256 fee, address recipient, uint256 index) private {

        uint256 tAmount = amount.mul(fee).div(FEES_DIVISOR);
        uint256 rAmount = tAmount.mul(currentRate);

        _reflectedBalances[recipient] = _reflectedBalances[recipient].add(rAmount);
        if(_isExcludedFromRewards[recipient])
            _balances[recipient] = _balances[recipient].add(tAmount);

        _addFeeCollectedAmount(index, tAmount);
    }
    
    /**
     * @dev When implemented this will convert the fee amount of tokens into ETH/BNB
     * and send to the recipient's wallet. Note that this reduces liquidity so it 
     * might be a good idea to add a % into the liquidity fee for % you take our through
     * this method (just a suggestions)
     */
    function _takeFeeToETH(uint256 amount, uint256 currentRate, uint256 fee, address recipient, uint256 index) private {
        _takeFee(amount, currentRate, fee, recipient, index);        
    }

    function _approveDelegate(address owner, address spender, uint256 amount) internal override {
        _approve(owner, spender, amount);
    }
}

contract PZENDEPLOYERcontract is PZEN{

    constructor() PZEN(Env.Testnet){
        // pre-approve the initial liquidity supply (to safe a bit of time)
        _approve(owner(),address(_router), ~uint256(0));
    }
}

/**
 * Todo (beta):
 *
 * - reorganize the sol file(s) to make put everything editable in a single .sol file
 *      and keep all other code in other .sol file(s)
 * - move variable values initialized in the contract to be constructor parameters
 * - add/remove setters/getter where appropriate
 * - add unit tests (via ganache-cli + truffle)
 * - add full dev evn (truffle) folders & files
 *
 * Todo:
 * 
 * - implement `_takeFeeToETH` (currently just calls `_takeFee`)
 * - change Uniswap to PancakeSwap in contract/interface names and local var names
 * - change ETH to BNB in names and comments
 */

/**
 * Tests passed:
 * 
 * - Tokenomics fees can be added/removed/edited 
 * - Tokenomics fees are correctly taken from each (qualifying) transaction
 * - The PFI fee is correctly distributed among holders (which are not excluded from rewards)
 */
        

Contract ABI

[{"type":"constructor","stateMutability":"nonpayable","inputs":[]},{"type":"event","name":"Approval","inputs":[{"type":"address","name":"owner","internalType":"address","indexed":true},{"type":"address","name":"spender","internalType":"address","indexed":true},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"LiquidityAdded","inputs":[{"type":"uint256","name":"tokenAmountSent","internalType":"uint256","indexed":false},{"type":"uint256","name":"ethAmountSent","internalType":"uint256","indexed":false},{"type":"uint256","name":"liquidity","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"ManagementTransferred","inputs":[{"type":"address","name":"previousManager","internalType":"address","indexed":true},{"type":"address","name":"newManager","internalType":"address","indexed":true}],"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":"RouterSet","inputs":[{"type":"address","name":"router","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"SwapAndLiquify","inputs":[{"type":"uint256","name":"tokensSwapped","internalType":"uint256","indexed":false},{"type":"uint256","name":"ethReceived","internalType":"uint256","indexed":false},{"type":"uint256","name":"tokensIntoLiquidity","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"SwapAndLiquifyEnabledUpdated","inputs":[{"type":"bool","name":"enabled","internalType":"bool","indexed":false}],"anonymous":false},{"type":"event","name":"Transfer","inputs":[{"type":"address","name":"from","internalType":"address","indexed":true},{"type":"address","name":"to","internalType":"address","indexed":true},{"type":"uint256","name":"value","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"allowance","inputs":[{"type":"address","name":"owner","internalType":"address"},{"type":"address","name":"spender","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"approve","inputs":[{"type":"address","name":"spender","internalType":"address"},{"type":"uint256","name":"amount","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"balanceOf","inputs":[{"type":"address","name":"account","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"burn","inputs":[{"type":"uint256","name":"amount","internalType":"uint256"}]},{"type":"function","stateMutability":"pure","outputs":[{"type":"uint8","name":"","internalType":"uint8"}],"name":"decimals","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"decreaseAllowance","inputs":[{"type":"address","name":"spender","internalType":"address"},{"type":"uint256","name":"subtractedValue","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"excludeFromReward","inputs":[{"type":"address","name":"account","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"getUnlockTime","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"includeInReward","inputs":[{"type":"address","name":"account","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"increaseAllowance","inputs":[{"type":"address","name":"spender","internalType":"address"},{"type":"uint256","name":"addedValue","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isExcludedFromFee","inputs":[{"type":"address","name":"account","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isExcludedFromReward","inputs":[{"type":"address","name":"account","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"lock","inputs":[{"type":"uint256","name":"time","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"manager","inputs":[]},{"type":"function","stateMutability":"pure","outputs":[{"type":"string","name":"","internalType":"string"}],"name":"name","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"owner","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"reflectionFromToken","inputs":[{"type":"uint256","name":"tAmount","internalType":"uint256"},{"type":"bool","name":"deductTransferFee","internalType":"bool"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"renounceOwnership","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setExcludedFromFee","inputs":[{"type":"address","name":"account","internalType":"address"},{"type":"bool","name":"value","internalType":"bool"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setPreseableEnabled","inputs":[{"type":"bool","name":"value","internalType":"bool"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setRouterAddress","inputs":[{"type":"address","name":"router","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setSwapAndLiquifyEnabled","inputs":[{"type":"bool","name":"enabled","internalType":"bool"}]},{"type":"function","stateMutability":"pure","outputs":[{"type":"string","name":"","internalType":"string"}],"name":"symbol","inputs":[]},{"type":"function","stateMutability":"pure","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalSupply","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"transfer","inputs":[{"type":"address","name":"recipient","internalType":"address"},{"type":"uint256","name":"amount","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"transferFrom","inputs":[{"type":"address","name":"sender","internalType":"address"},{"type":"address","name":"recipient","internalType":"address"},{"type":"uint256","name":"amount","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferManagement","inputs":[{"type":"address","name":"newManager","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferOwnership","inputs":[{"type":"address","name":"newOwner","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"unlock","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"withdrawLockedEth","inputs":[{"type":"address","name":"recipient","internalType":"address payable"}]},{"type":"receive","stateMutability":"payable"}]
              

Contract Creation Code

Verify & Publish
0x6080604052670c3663566a5800006000196200001c919062001898565b6000196200002b9190620017d1565b60045573e83b3c8fc65f6dacfccc90c8cac45a1f1dd38a2d600560006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555073e83b3c8fc65f6dacfccc90c8cac45a1f1dd38a2d600660006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550731414213562373095048801688724209698078569600760006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555073079086722c172eb0adc9886529d2b8139bc45667600860006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055507305ff2b0db69458a0750badebc4f9e13add608c7f601260016101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550737a250d5630b4cf539739df2c5dacb4c659f2488d601360006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550737a250d5630b4cf539739df2c5dacb4c659f2488d601460006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506001601660156101000a81548160ff021916908315150217905550348015620002a957600080fd5b50600080620002bd620006c560201b60201c565b9050806000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508073ffffffffffffffffffffffffffffffffffffffff16600073ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a35060006200036d620006c560201b60201c565b905080600360006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508073ffffffffffffffffffffffffffffffffffffffff16600073ffffffffffffffffffffffffffffffffffffffff167f80f15e9dbc60884fdb59fb8ed4fc48a9a689e028f055e893ed45ca5be67c5c8560405160405180910390a3506200041c620006cd60201b60201c565b600454600b6000620004336200079d60201b60201c565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506001600e6000620004876200079d60201b60201c565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506001600e60003073ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff02191690831515021790555062000550620005446200079d60201b60201c565b620007c660201b60201c565b6200056130620007c660201b60201c565b620005716200079d60201b60201c565b73ffffffffffffffffffffffffffffffffffffffff16600073ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef670c3663566a580000604051620005d891906200170e565b60405180910390a36200061281670c3663566a5800006103e8670c3663566a58000062000606919062001799565b6200096160201b60201c565b62000645601660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16620007c660201b60201c565b62000678600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16620007c660201b60201c565b50620006bf6200068d6200079d60201b60201c565b601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1660001962000b8160201b60201c565b62001a35565b600033905090565b620006e2600360c83062000d5460201b60201c565b62000718600180600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000d5460201b60201c565b6200072d600260003062000d5460201b60201c565b6200076460046014600560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000d5460201b60201c565b6200079b60046000600660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000d5460201b60201c565b565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6000600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541115620008a3576200085f600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205462000ec460201b60201c565b600c60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6001600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506010819080600181540180825580915050600190039060005260206000200160009091909190916101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b82601260006101000a81548160ff02191690836002811115620009ad577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b021790555060016002811115620009ed577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b601260009054906101000a900460ff16600281111562000a36577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b141562000a765762000a70601260019054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000f4460201b60201c565b62000b6e565b60028081111562000ab0577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b601260009054906101000a900460ff16600281111562000af9577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b141562000b395762000b33601360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000f4460201b60201c565b62000b6d565b62000b6c601460009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1662000f4460201b60201c565b5b5b8160178190555080601881905550505050565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff16141562000bf4576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040162000beb90620016a8565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16141562000c67576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040162000c5e90620016ec565b60405180910390fd5b80600d60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9258360405162000d4791906200170e565b60405180910390a3505050565b6009604051806080016040528085600581111562000d9b577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b81526020018481526020018373ffffffffffffffffffffffffffffffffffffffff1681526020016000815250908060018154018082558091505060019003906000526020600020906004020160009091909190915060008201518160000160006101000a81548160ff0219169083600581111562000e42577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b02179055506020820151816001015560408201518160020160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060608201518160030155505081600a600082825462000eb891906200173c565b92505081905550505050565b600060045482111562000f0e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040162000f0590620016ca565b60405180910390fd5b600062000f20620011a660201b60201c565b905062000f3c8184620011e060201b620022a71790919060201c565b915050919050565b60008190508073ffffffffffffffffffffffffffffffffffffffff1663c45a01556040518163ffffffff1660e01b815260040160206040518083038186803b15801562000f9057600080fd5b505afa15801562000fa5573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019062000fcb9190620015b8565b73ffffffffffffffffffffffffffffffffffffffff1663c9c65396308373ffffffffffffffffffffffffffffffffffffffff1663ad5c46486040518163ffffffff1660e01b815260040160206040518083038186803b1580156200102e57600080fd5b505afa15801562001043573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620010699190620015b8565b6040518363ffffffff1660e01b8152600401620010889291906200167b565b602060405180830381600087803b158015620010a357600080fd5b505af1158015620010b8573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190620010de9190620015b8565b601660006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555080601560006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff167fc6b438e6a8a59579ce6a4406cbd203b740e0d47b458aae6596339bcd40c40d1560405160405180910390a25050565b6000806000620011bb620011f860201b60201c565b91509150620011d98183620011e060201b620022a71790919060201c565b9250505090565b60008183620011f0919062001799565b905092915050565b600080600060045490506000670c3663566a580000905060005b6010805490508110156200152b5782600b60006010848154811062001260577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054118062001376575081600c6000601084815481106200130e577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054115b156200139557600454670c3663566a5800009450945050505062001585565b62001453600b600060108481548110620013d8577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054846200158960201b620022bd1790919060201c565b925062001513600c60006010848154811062001498577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054836200158960201b620022bd1790919060201c565b9150808062001522906200184a565b91505062001212565b5060008114806200155e57506200155b670c3663566a580000600454620011e060201b620022a71790919060201c565b82105b156200157c57600454670c3663566a58000093509350505062001585565b81819350935050505b9091565b60008183620015999190620017d1565b905092915050565b600081519050620015b28162001a1b565b92915050565b600060208284031215620015cb57600080fd5b6000620015db84828501620015a1565b91505092915050565b620015ef816200180c565b82525050565b600062001604602b836200172b565b915062001611826200192e565b604082019050919050565b60006200162b602a836200172b565b915062001638826200197d565b604082019050919050565b6000620016526029836200172b565b91506200165f82620019cc565b604082019050919050565b620016758162001840565b82525050565b6000604082019050620016926000830185620015e4565b620016a16020830184620015e4565b9392505050565b60006020820190508181036000830152620016c381620015f5565b9050919050565b60006020820190508181036000830152620016e5816200161c565b9050919050565b60006020820190508181036000830152620017078162001643565b9050919050565b60006020820190506200172560008301846200166a565b92915050565b600082825260208201905092915050565b6000620017498262001840565b9150620017568362001840565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff038211156200178e576200178d620018d0565b5b828201905092915050565b6000620017a68262001840565b9150620017b38362001840565b925082620017c657620017c5620018ff565b5b828204905092915050565b6000620017de8262001840565b9150620017eb8362001840565b925082821015620018015762001800620018d0565b5b828203905092915050565b6000620018198262001820565b9050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b6000620018578262001840565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8214156200188d576200188c620018d0565b5b600182019050919050565b6000620018a58262001840565b9150620018b28362001840565b925082620018c557620018c4620018ff565b5b828206905092915050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b7f42617365526669546f6b656e3a20617070726f76652066726f6d20746865207a60008201527f65726f2061646472657373000000000000000000000000000000000000000000602082015250565b7f416d6f756e74206d757374206265206c657373207468616e20746f74616c207260008201527f65666c656374696f6e7300000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a20617070726f766520746f20746865207a657260008201527f6f20616464726573730000000000000000000000000000000000000000000000602082015250565b62001a26816200180c565b811462001a3257600080fd5b50565b615c748062001a456000396000f3fe6080604052600436106101d15760003560e01c806370a08231116100f7578063a69df4b511610095578063dd46706411610064578063dd467064146106a5578063dd62ed3e146106ce578063e4edf8521461070b578063f2fde38b14610734576101d8565b8063a69df4b5146105ff578063a9059cbb14610616578063b7671a0d14610653578063c49b9a801461067c576101d8565b806388f82020116100d157806388f820201461052f5780638da5cb5b1461056c57806395d89b4114610597578063a457c2d7146105c2576101d8565b806370a08231146104b2578063715018a6146104ef57806374778cdc14610506576101d8565b806341cb87fc1161016f57806352390c021161013e57806352390c02146103f85780635342acb414610421578063602bc62b1461045e5780636612e66f14610489576101d8565b806341cb87fc1461033e57806342966c68146103675780634549b03914610390578063481c6a75146103cd576101d8565b806323b872dd116101ab57806323b872dd14610270578063313ce567146102ad5780633685d419146102d85780633950935114610301576101d8565b806306fdde03146101dd578063095ea7b31461020857806318160ddd14610245576101d8565b366101d857005b600080fd5b3480156101e957600080fd5b506101f261075d565b6040516101ff9190614ea3565b60405180910390f35b34801561021457600080fd5b5061022f600480360381019061022a919061489c565b61079a565b60405161023c9190614e88565b60405180910390f35b34801561025157600080fd5b5061025a6107b8565b60405161026791906151a5565b60405180910390f35b34801561027c57600080fd5b5061029760048036038101906102929190614811565b6107c8565b6040516102a49190614e88565b60405180910390f35b3480156102b957600080fd5b506102c26108a1565b6040516102cf9190615251565b60405180910390f35b3480156102e457600080fd5b506102ff60048036038101906102fa919061475a565b6108aa565b005b34801561030d57600080fd5b506103286004803603810190610323919061489c565b610c91565b6040516103359190614e88565b60405180910390f35b34801561034a57600080fd5b506103656004803603810190610360919061475a565b610d44565b005b34801561037357600080fd5b5061038e60048036038101906103899190614901565b610de7565b005b34801561039c57600080fd5b506103b760048036038101906103b2919061492a565b6110f0565b6040516103c491906151a5565b60405180910390f35b3480156103d957600080fd5b506103e261118b565b6040516103ef9190614de3565b60405180910390f35b34801561040457600080fd5b5061041f600480360381019061041a919061475a565b6111b5565b005b34801561042d57600080fd5b506104486004803603810190610443919061475a565b6112e3565b6040516104559190614e88565b60405180910390f35b34801561046a57600080fd5b50610473611339565b60405161048091906151a5565b60405180910390f35b34801561049557600080fd5b506104b060048036038101906104ab9190614860565b611343565b005b3480156104be57600080fd5b506104d960048036038101906104d4919061475a565b611433565b6040516104e691906151a5565b60405180910390f35b3480156104fb57600080fd5b5061050461151e565b005b34801561051257600080fd5b5061052d600480360381019061052891906148d8565b611671565b005b34801561053b57600080fd5b506105566004803603810190610551919061475a565b611725565b6040516105639190614e88565b60405180910390f35b34801561057857600080fd5b5061058161177b565b60405161058e9190614de3565b60405180910390f35b3480156105a357600080fd5b506105ac6117a4565b6040516105b99190614ea3565b60405180910390f35b3480156105ce57600080fd5b506105e960048036038101906105e4919061489c565b6117e1565b6040516105f69190614e88565b60405180910390f35b34801561060b57600080fd5b506106146118ae565b005b34801561062257600080fd5b5061063d6004803603810190610638919061489c565b611a82565b60405161064a9190614e88565b60405180910390f35b34801561065f57600080fd5b5061067a600480360381019061067591906147ac565b611aa0565b005b34801561068857600080fd5b506106a3600480360381019061069e91906148d8565b611c46565b005b3480156106b157600080fd5b506106cc60048036038101906106c79190614901565b611d40565b005b3480156106da57600080fd5b506106f560048036038101906106f091906147d5565b611f07565b60405161070291906151a5565b60405180910390f35b34801561071757600080fd5b50610732600480360381019061072d919061475a565b611f8e565b005b34801561074057600080fd5b5061075b6004803603810190610756919061475a565b6120e5565b005b60606040518060400160405280600681526020017f504c535a454e0000000000000000000000000000000000000000000000000000815250905090565b60006107ae6107a76122d3565b84846122db565b6001905092915050565b6000670c3663566a580000905090565b60006107d58484846124a6565b610896846107e16122d3565b61089185604051806060016040528060288152602001615bf260289139600d60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006108476122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205461287b9092919063ffffffff16565b6122db565b600190509392505050565b60006009905090565b6108b26122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461093f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610936906150a5565b60405180910390fd5b600f60008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff166109cb576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016109c290614fa5565b60405180910390fd5b60005b601080549050811015610c8d578173ffffffffffffffffffffffffffffffffffffffff1660108281548110610a2c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161415610c7a5760106001601080549050610a8791906153a2565b81548110610abe577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1660108281548110610b23577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506000600c60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506000600f60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506010805480610c40577f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fd5b6001900381819060005260206000200160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690559055610c8d565b8080610c8590615482565b9150506109ce565b5050565b6000610d3a610c9e6122d3565b84610d3585600d6000610caf6122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b6122db565b6001905092915050565b610d4c6122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614610ddb576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610dd290615125565b60405180910390fd5b610de4816128e6565b50565b6000610df16122d3565b9050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415610e63576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610e5a90615185565b60405180910390fd5b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415610ef4576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610eeb90614f85565b60405180910390fd5b6000610eff82611433565b905082811015610f44576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610f3b90615045565b60405180910390fd5b6000610f60610f51612b3a565b85612b6590919063ffffffff16565b9050610fb481600b60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600b60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156110df5761109b84600c60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600c60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6110ea838583612b7b565b50505050565b6000670c3663566a58000083111561113d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161113490615005565b60405180910390fd5b8161115e57600061114f846000612e2e565b50505050905080915050611185565b600061117a8461117561116f6122d3565b87612eeb565b612e2e565b505050915050809150505b92915050565b6000600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6111bd6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461124a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611241906150a5565b60405180910390fd5b600f60008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156112d7576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016112ce90614f65565b60405180910390fd5b6112e081612f07565b50565b6000600e60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff169050919050565b6000600254905090565b61134b6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16146113d8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016113cf906150a5565b60405180910390fd5b80600e60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055505050565b6000600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156114ce57600c60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020549050611519565b611516600b60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054613099565b90505b919050565b6115266122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16146115b3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016115aa906150a5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a360008060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550565b6116796122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611708576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016116ff90615125565b60405180910390fd5b80600360146101000a81548160ff02191690831515021790555050565b6000600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff169050919050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b60606040518060400160405280600481526020017f505a454e00000000000000000000000000000000000000000000000000000000815250905090565b60006118a46117ee6122d3565b8461189f85604051806060016040528060258152602001615c1a60259139600d60006118186122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205461287b9092919063ffffffff16565b6122db565b6001905092915050565b3373ffffffffffffffffffffffffffffffffffffffff16600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461193e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161193590614f05565b60405180910390fd5b6002544211611982576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161197990614ec5565b60405180910390fd5b600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a3600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff166000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550565b6000611a96611a8f6122d3565b84846124a6565b6001905092915050565b611aa86122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611b37576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611b2e90615125565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415611ba7576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611b9e90615085565b60405180910390fd5b600060115411611bec576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611be3906150e5565b60405180910390fd5b6000601154905060006011819055508173ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015611c41573d6000803e3d6000fd5b505050565b611c4e6122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611cdd576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611cd490615125565b60405180910390fd5b80601660156101000a81548160ff0219169083151502179055507f53726dfcaf90650aa7eb35524f4d3220f07413c8d6cb404cc8c18bf5591bc159601660159054906101000a900460ff16604051611d359190614e88565b60405180910390a150565b611d486122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611dd5576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611dcc906150a5565b60405180910390fd5b60008054906101000a900473ffffffffffffffffffffffffffffffffffffffff16600160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060008060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508042611e8391906152c1565b600281905550600073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a350565b6000600d60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054905092915050565b611f966122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614612025576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161201c90615125565b60405180910390fd5b8073ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f80f15e9dbc60884fdb59fb8ed4fc48a9a689e028f055e893ed45ca5be67c5c8560405160405180910390a380600360006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6120ed6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461217a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612171906150a5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614156121ea576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016121e190614f45565b60405180910390fd5b8073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a3806000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b600081836122b59190615317565b905092915050565b600081836122cb91906153a2565b905092915050565b600033905090565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff16141561234b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161234290614ee5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614156123bb576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016123b290615165565b60405180910390fd5b80600d60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9258360405161249991906151a5565b60405180910390a3505050565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612516576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161250d90614fc5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415612586576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161257d90615065565b60405180910390fd5b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612617576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161260e90614fe5565b60405180910390fd5b6000811161265a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612651906150c5565b60405180910390fd5b600060019050600360149054906101000a900460ff161561267e57600090506127b2565b670c3663566a5800008211801561269b575061269984613107565b155b80156126ad57506126ab83613146565b155b156126ed576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016126e490615025565b60405180910390fd5b60006003670c3663566a5800006127049190615317565b118015612717575061271584613107565b155b8015612729575061272783613146565b155b801561273b5750612739836131dd565b155b156127b157600061274b84611433565b90506003670c3663566a5800006127629190615317565b838261276e91906152c1565b11156127af576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016127a690615105565b60405180910390fd5b505b5b600e60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16806128535750600e60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff165b1561285d57600090505b61286984848484613237565b6128758484848461326a565b50505050565b60008383111582906128c3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016128ba9190614ea3565b60405180910390fd5b5082840390509392505050565b600081836128de91906152c1565b905092915050565b60008190508073ffffffffffffffffffffffffffffffffffffffff1663c45a01556040518163ffffffff1660e01b815260040160206040518083038186803b15801561293157600080fd5b505afa158015612945573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906129699190614783565b73ffffffffffffffffffffffffffffffffffffffff1663c9c65396308373ffffffffffffffffffffffffffffffffffffffff1663ad5c46486040518163ffffffff1660e01b815260040160206040518083038186803b1580156129cb57600080fd5b505afa1580156129df573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612a039190614783565b6040518363ffffffff1660e01b8152600401612a20929190614dfe565b602060405180830381600087803b158015612a3a57600080fd5b505af1158015612a4e573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612a729190614783565b601660006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555080601560006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff167fc6b438e6a8a59579ce6a4406cbd203b740e0d47b458aae6596339bcd40c40d1560405160405180910390a25050565b6000806000612b47613614565b91509150612b5e81836122a790919063ffffffff16565b9250505090565b60008183612b739190615348565b905092915050565b612bef81600b6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff1615612da257612d3c82600c6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef84604051612e2191906151a5565b60405180910390a3505050565b600080600080600080612e6261271061ffff16612e54898b612b6590919063ffffffff16565b6122a790919063ffffffff16565b90506000612e79828a6122bd90919063ffffffff16565b90506000612e85612b3a565b90506000612e9c828c612b6590919063ffffffff16565b90506000612eb38386612b6590919063ffffffff16565b90506000612eca82846122bd90919063ffffffff16565b905082818e87879a509a509a509a509a505050505050509295509295909350565b6000612eff612ef984611433565b83613982565b905092915050565b6000600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541115612fdb57612f97600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054613099565b600c60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6001600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506010819080600181540180825580915050600190039060005260206000200160009091909190916101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b60006004548211156130e0576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016130d790614f25565b60405180910390fd5b60006130ea612b3a565b90506130ff81846122a790919063ffffffff16565b915050919050565b600061311161177b565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16149050919050565b600061315061177b565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614806131d65750600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16145b9050919050565b6000601660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16149050919050565b600360149054906101000a900460ff1661326457600061325630611433565b9050613262818661398f565b505b50505050565b60006132768584612eeb565b90508161328257600090505b60008060008060006132948887612e2e565b945094509450945094506132f085600b60008d73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600b60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208190555061338584600b60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156134b05761346c83600c60008d73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600c60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b600f60008a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156135985761355482600c60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6135a3888288613a48565b8873ffffffffffffffffffffffffffffffffffffffff168a73ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef8460405161360091906151a5565b60405180910390a350505050505050505050565b600080600060045490506000670c3663566a580000905060005b60108054905081101561392e5782600b60006010848154811061367a577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054118061378e575081600c600060108481548110613726577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054115b156137ab57600454670c3663566a5800009450945050505061397e565b613861600b6000601084815481106137ec577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054846122bd90919063ffffffff16565b9250613919600c6000601084815481106138a4577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054836122bd90919063ffffffff16565b9150808061392690615482565b91505061362e565b5060008114806139595750613956670c3663566a5800006004546122a790919063ffffffff16565b82105b1561397557600454670c3663566a58000093509350505061397e565b81819350935050505b9091565b6000600a54905092915050565b601754821061399e5760175491505b600060185483101590508080156139c15750601660159054906101000a900460ff165b80156139da5750601660149054906101000a900460ff16155b8015613a345750601660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614155b15613a4357613a4283613a7a565b5b505050565b600081118015613a655750600360149054906101000a900460ff16155b15613a7557613a748383613b50565b5b505050565b6001601660146101000a81548160ff0219169083151502179055506000613aab6002836122a790919063ffffffff16565b90506000613ac282846122bd90919063ffffffff16565b90506000479050613ad283613df2565b6000613ae782476122bd90919063ffffffff16565b9050613af383826140b6565b7f17bbfb9a6069321b6ded73bd96327c9e6b7212a5cd51ff219cd61370acafb561848285604051613b269392919061521a565b60405180910390a1505050506000601660146101000a81548160ff02191690831515021790555050565b600360149054906101000a900460ff1615613b6a57613dee565b6000613b746141f7565b905060005b81811015613deb576000806000613b8f84614204565b509250925092506000821415613ba757505050613dd8565b60036005811115613be1577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613c1a577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613c3157613c2c87878487614337565b613dd4565b60016005811115613c6b577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613ca4577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613cbb57613cb6878784876143aa565b613dd3565b60006005811115613cf5577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613d2e577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613d3957613dd2565b600580811115613d72577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613dab577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613dc357613dbe878784848861440d565b613dd1565b613dd08787848488614421565b5b5b5b5b5050505b8080613de390615482565b915050613b79565b50505b5050565b6000600267ffffffffffffffff811115613e35577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b604051908082528060200260200182016040528015613e635781602001602082028036833780820191505090505b5090503081600081518110613ea1577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b602002602001019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff1681525050601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663ad5c46486040518163ffffffff1660e01b815260040160206040518083038186803b158015613f4357600080fd5b505afa158015613f57573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190613f7b9190614783565b81600181518110613fb5577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b602002602001019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff168152505061401c30601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16846145f7565b601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663791ac9478360008430426040518663ffffffff1660e01b81526004016140809594939291906151c0565b600060405180830381600087803b15801561409a57600080fd5b505af11580156140ae573d6000803e3d6000fd5b505050505050565b6140e330601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16846145f7565b6000806000601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663f305d71985308860008061413461177b565b426040518863ffffffff1660e01b815260040161415696959493929190614e27565b6060604051808303818588803b15801561416f57600080fd5b505af1158015614183573d6000803e3d6000fd5b50505050506040513d601f19601f820116820180604052508101906141a89190614966565b925092509250476011819055507fd7f28048575eead8851d024ead087913957dfb4fd1a02b4d1573f5352a5a2be38383836040516141e89392919061521a565b60405180910390a15050505050565b6000600980549050905090565b600080600080600061421586614607565b6040518060800160405290816000820160009054906101000a900460ff16600581111561426b577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b60058111156142a3577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b8152602001600182015481526020016002820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001600382015481525050905080600001518160200151826040015183606001519450945094509450509193509193565b600061436461271061ffff166143568588612b6590919063ffffffff16565b6122a790919063ffffffff16565b9050600061437b8583612b6590919063ffffffff16565b9050614392816004546122bd90919063ffffffff16565b6004819055506143a283836146ab565b505050505050565b60006143d761271061ffff166143c98588612b6590919063ffffffff16565b6122a790919063ffffffff16565b905060006143ee8583612b6590919063ffffffff16565b90506143fb308383612b7b565b61440583836146ab565b505050505050565b61441a8585858585614421565b5050505050565b600061444e61271061ffff166144408689612b6590919063ffffffff16565b6122a790919063ffffffff16565b905060006144658683612b6590919063ffffffff16565b90506144b981600b60008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156145e4576145a082600c60008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6145ee83836146ab565b50505050505050565b6146028383836122db565b505050565b600080821015801561461d575060098054905082105b61465c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161465390615145565b60405180910390fd5b60098281548110614696577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90600052602060002090600402019050919050565b60006146b683614607565b90506146cf8282600301546128d090919063ffffffff16565b8160030181905550505050565b6000813590506146eb81615b95565b92915050565b60008151905061470081615b95565b92915050565b60008135905061471581615bac565b92915050565b60008135905061472a81615bc3565b92915050565b60008135905061473f81615bda565b92915050565b60008151905061475481615bda565b92915050565b60006020828403121561476c57600080fd5b600061477a848285016146dc565b91505092915050565b60006020828403121561479557600080fd5b60006147a3848285016146f1565b91505092915050565b6000602082840312156147be57600080fd5b60006147cc84828501614706565b91505092915050565b600080604083850312156147e857600080fd5b60006147f6858286016146dc565b9250506020614807858286016146dc565b9150509250929050565b60008060006060848603121561482657600080fd5b6000614834868287016146dc565b9350506020614845868287016146dc565b925050604061485686828701614730565b9150509250925092565b6000806040838503121561487357600080fd5b6000614881858286016146dc565b92505060206148928582860161471b565b9150509250929050565b600080604083850312156148af57600080fd5b60006148bd858286016146dc565b92505060206148ce85828601614730565b9150509250929050565b6000602082840312156148ea57600080fd5b60006148f88482850161471b565b91505092915050565b60006020828403121561491357600080fd5b600061492184828501614730565b91505092915050565b6000806040838503121561493d57600080fd5b600061494b85828601614730565b925050602061495c8582860161471b565b9150509250929050565b60008060006060848603121561497b57600080fd5b600061498986828701614745565b935050602061499a86828701614745565b92505060406149ab86828701614745565b9150509250925092565b60006149c183836149cd565b60208301905092915050565b6149d6816153d6565b82525050565b6149e5816153d6565b82525050565b60006149f68261527c565b614a00818561529f565b9350614a0b8361526c565b8060005b83811015614a3c578151614a2388826149b5565b9750614a2e83615292565b925050600181019050614a0f565b5085935050505092915050565b614a52816153fa565b82525050565b614a618161543d565b82525050565b6000614a7282615287565b614a7c81856152b0565b9350614a8c81856020860161544f565b614a9581615529565b840191505092915050565b6000614aad601c836152b0565b9150614ab88261553a565b602082019050919050565b6000614ad0602b836152b0565b9150614adb82615563565b604082019050919050565b6000614af3602c836152b0565b9150614afe826155b2565b604082019050919050565b6000614b16602a836152b0565b9150614b2182615601565b604082019050919050565b6000614b396026836152b0565b9150614b4482615650565b604082019050919050565b6000614b5c6017836152b0565b9150614b678261569f565b602082019050919050565b6000614b7f6028836152b0565b9150614b8a826156c8565b604082019050919050565b6000614ba26017836152b0565b9150614bad82615717565b602082019050919050565b6000614bc5602c836152b0565b9150614bd082615740565b604082019050919050565b6000614be8602c836152b0565b9150614bf38261578f565b604082019050919050565b6000614c0b601f836152b0565b9150614c16826157de565b602082019050919050565b6000614c2e6028836152b0565b9150614c3982615807565b604082019050919050565b6000614c516029836152b0565b9150614c5c82615856565b604082019050919050565b6000614c74602a836152b0565b9150614c7f826158a5565b604082019050919050565b6000614c976033836152b0565b9150614ca2826158f4565b604082019050919050565b6000614cba6020836152b0565b9150614cc582615943565b602082019050919050565b6000614cdd6029836152b0565b9150614ce88261596c565b604082019050919050565b6000614d006026836152b0565b9150614d0b826159bb565b604082019050919050565b6000614d23602d836152b0565b9150614d2e82615a0a565b604082019050919050565b6000614d466025836152b0565b9150614d5182615a59565b604082019050919050565b6000614d696033836152b0565b9150614d7482615aa8565b604082019050919050565b6000614d8c6029836152b0565b9150614d9782615af7565b604082019050919050565b6000614daf6028836152b0565b9150614dba82615b46565b604082019050919050565b614dce81615426565b82525050565b614ddd81615430565b82525050565b6000602082019050614df860008301846149dc565b92915050565b6000604082019050614e1360008301856149dc565b614e2060208301846149dc565b9392505050565b600060c082019050614e3c60008301896149dc565b614e496020830188614dc5565b614e566040830187614a58565b614e636060830186614a58565b614e7060808301856149dc565b614e7d60a0830184614dc5565b979650505050505050565b6000602082019050614e9d6000830184614a49565b92915050565b60006020820190508181036000830152614ebd8184614a67565b905092915050565b60006020820190508181036000830152614ede81614aa0565b9050919050565b60006020820190508181036000830152614efe81614ac3565b9050919050565b60006020820190508181036000830152614f1e81614ae6565b9050919050565b60006020820190508181036000830152614f3e81614b09565b9050919050565b60006020820190508181036000830152614f5e81614b2c565b9050919050565b60006020820190508181036000830152614f7e81614b4f565b9050919050565b60006020820190508181036000830152614f9e81614b72565b9050919050565b60006020820190508181036000830152614fbe81614b95565b9050919050565b60006020820190508181036000830152614fde81614bb8565b9050919050565b60006020820190508181036000830152614ffe81614bdb565b9050919050565b6000602082019050818103600083015261501e81614bfe565b9050919050565b6000602082019050818103600083015261503e81614c21565b9050919050565b6000602082019050818103600083015261505e81614c44565b9050919050565b6000602082019050818103600083015261507e81614c67565b9050919050565b6000602082019050818103600083015261509e81614c8a565b9050919050565b600060208201905081810360008301526150be81614cad565b9050919050565b600060208201905081810360008301526150de81614cd0565b9050919050565b600060208201905081810360008301526150fe81614cf3565b9050919050565b6000602082019050818103600083015261511e81614d16565b9050919050565b6000602082019050818103600083015261513e81614d39565b9050919050565b6000602082019050818103600083015261515e81614d5c565b9050919050565b6000602082019050818103600083015261517e81614d7f565b9050919050565b6000602082019050818103600083015261519e81614da2565b9050919050565b60006020820190506151ba6000830184614dc5565b92915050565b600060a0820190506151d56000830188614dc5565b6151e26020830187614a58565b81810360408301526151f481866149eb565b905061520360608301856149dc565b6152106080830184614dc5565b9695505050505050565b600060608201905061522f6000830186614dc5565b61523c6020830185614dc5565b6152496040830184614dc5565b949350505050565b60006020820190506152666000830184614dd4565b92915050565b6000819050602082019050919050565b600081519050919050565b600081519050919050565b6000602082019050919050565b600082825260208201905092915050565b600082825260208201905092915050565b60006152cc82615426565b91506152d783615426565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561530c5761530b6154cb565b5b828201905092915050565b600061532282615426565b915061532d83615426565b92508261533d5761533c6154fa565b5b828204905092915050565b600061535382615426565b915061535e83615426565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0483118215151615615397576153966154cb565b5b828202905092915050565b60006153ad82615426565b91506153b883615426565b9250828210156153cb576153ca6154cb565b5b828203905092915050565b60006153e182615406565b9050919050565b60006153f382615406565b9050919050565b60008115159050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b600060ff82169050919050565b600061544882615426565b9050919050565b60005b8381101561546d578082015181840152602081019050615452565b8381111561547c576000848401525b50505050565b600061548d82615426565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8214156154c0576154bf6154cb565b5b600182019050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b6000601f19601f8301169050919050565b7f54686520636f6e7472616374206973207374696c6c206c6f636b656400000000600082015250565b7f42617365526669546f6b656e3a20617070726f76652066726f6d20746865207a60008201527f65726f2061646472657373000000000000000000000000000000000000000000602082015250565b7f4f6e6c79207468652070726576696f7573206f776e65722063616e20756e6c6f60008201527f636b206f6e776572736869700000000000000000000000000000000000000000602082015250565b7f416d6f756e74206d757374206265206c657373207468616e20746f74616c207260008201527f65666c656374696f6e7300000000000000000000000000000000000000000000602082015250565b7f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160008201527f6464726573730000000000000000000000000000000000000000000000000000602082015250565b7f4163636f756e74206973206e6f7420696e636c75646564000000000000000000600082015250565b7f42617365526669546f6b656e3a206275726e2066726f6d20746865206275726e60008201527f2061646472657373000000000000000000000000000000000000000000000000602082015250565b7f4163636f756e74206973206e6f74206578636c75646564000000000000000000600082015250565b7f42617365526669546f6b656e3a207472616e736665722066726f6d207468652060008201527f7a65726f20616464726573730000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a207472616e736665722066726f6d207468652060008201527f6275726e20616464726573730000000000000000000000000000000000000000602082015250565b7f416d6f756e74206d757374206265206c657373207468616e20737570706c7900600082015250565b7f5472616e7366657220616d6f756e74206578636565647320746865206d61785460008201527f78416d6f756e742e000000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a206275726e20616d6f756e742065786365656460008201527f732062616c616e63650000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a207472616e7366657220746f20746865207a6560008201527f726f206164647265737300000000000000000000000000000000000000000000602082015250565b7f43616e6e6f7420776974686472617720746865204554482062616c616e63652060008201527f746f20746865207a65726f206164647265737300000000000000000000000000602082015250565b7f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572600082015250565b7f5472616e7366657220616d6f756e74206d75737420626520677265617465722060008201527f7468616e207a65726f0000000000000000000000000000000000000000000000602082015250565b7f546865204554482062616c616e6365206d75737420626520677265617465722060008201527f7468616e20300000000000000000000000000000000000000000000000000000602082015250565b7f4e65772062616c616e636520776f756c642065786365656420746865206d617860008201527f57616c6c657442616c616e636500000000000000000000000000000000000000602082015250565b7f4d616e61676561626c653a2063616c6c6572206973206e6f7420746865206d6160008201527f6e61676572000000000000000000000000000000000000000000000000000000602082015250565b7f4665657353657474696e67732e5f6765744665655374727563743a204665652060008201527f696e646578206f7574206f6620626f756e647300000000000000000000000000602082015250565b7f42617365526669546f6b656e3a20617070726f766520746f20746865207a657260008201527f6f20616464726573730000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a206275726e2066726f6d20746865207a65726f60008201527f2061646472657373000000000000000000000000000000000000000000000000602082015250565b615b9e816153d6565b8114615ba957600080fd5b50565b615bb5816153e8565b8114615bc057600080fd5b50565b615bcc816153fa565b8114615bd757600080fd5b50565b615be381615426565b8114615bee57600080fd5b5056fe45524332303a207472616e7366657220616d6f756e74206578636565647320616c6c6f77616e636545524332303a2064656372656173656420616c6c6f77616e63652062656c6f77207a65726fa26469706673582212203e43835e1879172c1066111b820887ae4055bbb1e1a018e20e8caed9e8b4de8064736f6c63430008040033

Deployed ByteCode

0x6080604052600436106101d15760003560e01c806370a08231116100f7578063a69df4b511610095578063dd46706411610064578063dd467064146106a5578063dd62ed3e146106ce578063e4edf8521461070b578063f2fde38b14610734576101d8565b8063a69df4b5146105ff578063a9059cbb14610616578063b7671a0d14610653578063c49b9a801461067c576101d8565b806388f82020116100d157806388f820201461052f5780638da5cb5b1461056c57806395d89b4114610597578063a457c2d7146105c2576101d8565b806370a08231146104b2578063715018a6146104ef57806374778cdc14610506576101d8565b806341cb87fc1161016f57806352390c021161013e57806352390c02146103f85780635342acb414610421578063602bc62b1461045e5780636612e66f14610489576101d8565b806341cb87fc1461033e57806342966c68146103675780634549b03914610390578063481c6a75146103cd576101d8565b806323b872dd116101ab57806323b872dd14610270578063313ce567146102ad5780633685d419146102d85780633950935114610301576101d8565b806306fdde03146101dd578063095ea7b31461020857806318160ddd14610245576101d8565b366101d857005b600080fd5b3480156101e957600080fd5b506101f261075d565b6040516101ff9190614ea3565b60405180910390f35b34801561021457600080fd5b5061022f600480360381019061022a919061489c565b61079a565b60405161023c9190614e88565b60405180910390f35b34801561025157600080fd5b5061025a6107b8565b60405161026791906151a5565b60405180910390f35b34801561027c57600080fd5b5061029760048036038101906102929190614811565b6107c8565b6040516102a49190614e88565b60405180910390f35b3480156102b957600080fd5b506102c26108a1565b6040516102cf9190615251565b60405180910390f35b3480156102e457600080fd5b506102ff60048036038101906102fa919061475a565b6108aa565b005b34801561030d57600080fd5b506103286004803603810190610323919061489c565b610c91565b6040516103359190614e88565b60405180910390f35b34801561034a57600080fd5b506103656004803603810190610360919061475a565b610d44565b005b34801561037357600080fd5b5061038e60048036038101906103899190614901565b610de7565b005b34801561039c57600080fd5b506103b760048036038101906103b2919061492a565b6110f0565b6040516103c491906151a5565b60405180910390f35b3480156103d957600080fd5b506103e261118b565b6040516103ef9190614de3565b60405180910390f35b34801561040457600080fd5b5061041f600480360381019061041a919061475a565b6111b5565b005b34801561042d57600080fd5b506104486004803603810190610443919061475a565b6112e3565b6040516104559190614e88565b60405180910390f35b34801561046a57600080fd5b50610473611339565b60405161048091906151a5565b60405180910390f35b34801561049557600080fd5b506104b060048036038101906104ab9190614860565b611343565b005b3480156104be57600080fd5b506104d960048036038101906104d4919061475a565b611433565b6040516104e691906151a5565b60405180910390f35b3480156104fb57600080fd5b5061050461151e565b005b34801561051257600080fd5b5061052d600480360381019061052891906148d8565b611671565b005b34801561053b57600080fd5b506105566004803603810190610551919061475a565b611725565b6040516105639190614e88565b60405180910390f35b34801561057857600080fd5b5061058161177b565b60405161058e9190614de3565b60405180910390f35b3480156105a357600080fd5b506105ac6117a4565b6040516105b99190614ea3565b60405180910390f35b3480156105ce57600080fd5b506105e960048036038101906105e4919061489c565b6117e1565b6040516105f69190614e88565b60405180910390f35b34801561060b57600080fd5b506106146118ae565b005b34801561062257600080fd5b5061063d6004803603810190610638919061489c565b611a82565b60405161064a9190614e88565b60405180910390f35b34801561065f57600080fd5b5061067a600480360381019061067591906147ac565b611aa0565b005b34801561068857600080fd5b506106a3600480360381019061069e91906148d8565b611c46565b005b3480156106b157600080fd5b506106cc60048036038101906106c79190614901565b611d40565b005b3480156106da57600080fd5b506106f560048036038101906106f091906147d5565b611f07565b60405161070291906151a5565b60405180910390f35b34801561071757600080fd5b50610732600480360381019061072d919061475a565b611f8e565b005b34801561074057600080fd5b5061075b6004803603810190610756919061475a565b6120e5565b005b60606040518060400160405280600681526020017f504c535a454e0000000000000000000000000000000000000000000000000000815250905090565b60006107ae6107a76122d3565b84846122db565b6001905092915050565b6000670c3663566a580000905090565b60006107d58484846124a6565b610896846107e16122d3565b61089185604051806060016040528060288152602001615bf260289139600d60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006108476122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205461287b9092919063ffffffff16565b6122db565b600190509392505050565b60006009905090565b6108b26122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461093f576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610936906150a5565b60405180910390fd5b600f60008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff166109cb576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016109c290614fa5565b60405180910390fd5b60005b601080549050811015610c8d578173ffffffffffffffffffffffffffffffffffffffff1660108281548110610a2c577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161415610c7a5760106001601080549050610a8791906153a2565b81548110610abe577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1660108281548110610b23577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055506000600c60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055506000600f60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506010805480610c40577f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fd5b6001900381819060005260206000200160006101000a81549073ffffffffffffffffffffffffffffffffffffffff02191690559055610c8d565b8080610c8590615482565b9150506109ce565b5050565b6000610d3a610c9e6122d3565b84610d3585600d6000610caf6122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008973ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b6122db565b6001905092915050565b610d4c6122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614610ddb576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610dd290615125565b60405180910390fd5b610de4816128e6565b50565b6000610df16122d3565b9050600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415610e63576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610e5a90615185565b60405180910390fd5b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415610ef4576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610eeb90614f85565b60405180910390fd5b6000610eff82611433565b905082811015610f44576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401610f3b90615045565b60405180910390fd5b6000610f60610f51612b3a565b85612b6590919063ffffffff16565b9050610fb481600b60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600b60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156110df5761109b84600c60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600c60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6110ea838583612b7b565b50505050565b6000670c3663566a58000083111561113d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161113490615005565b60405180910390fd5b8161115e57600061114f846000612e2e565b50505050905080915050611185565b600061117a8461117561116f6122d3565b87612eeb565b612e2e565b505050915050809150505b92915050565b6000600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b6111bd6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461124a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611241906150a5565b60405180910390fd5b600f60008273ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156112d7576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016112ce90614f65565b60405180910390fd5b6112e081612f07565b50565b6000600e60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff169050919050565b6000600254905090565b61134b6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16146113d8576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016113cf906150a5565b60405180910390fd5b80600e60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055505050565b6000600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156114ce57600c60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020549050611519565b611516600b60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054613099565b90505b919050565b6115266122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16146115b3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016115aa906150a5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a360008060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550565b6116796122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611708576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016116ff90615125565b60405180910390fd5b80600360146101000a81548160ff02191690831515021790555050565b6000600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff169050919050565b60008060009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16905090565b60606040518060400160405280600481526020017f505a454e00000000000000000000000000000000000000000000000000000000815250905090565b60006118a46117ee6122d3565b8461189f85604051806060016040528060258152602001615c1a60259139600d60006118186122d3565b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000205461287b9092919063ffffffff16565b6122db565b6001905092915050565b3373ffffffffffffffffffffffffffffffffffffffff16600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461193e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161193590614f05565b60405180910390fd5b6002544211611982576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161197990614ec5565b60405180910390fd5b600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a3600160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff166000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff160217905550565b6000611a96611a8f6122d3565b84846124a6565b6001905092915050565b611aa86122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611b37576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611b2e90615125565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff161415611ba7576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611b9e90615085565b60405180910390fd5b600060115411611bec576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611be3906150e5565b60405180910390fd5b6000601154905060006011819055508173ffffffffffffffffffffffffffffffffffffffff166108fc829081150290604051600060405180830381858888f19350505050158015611c41573d6000803e3d6000fd5b505050565b611c4e6122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611cdd576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611cd490615125565b60405180910390fd5b80601660156101000a81548160ff0219169083151502179055507f53726dfcaf90650aa7eb35524f4d3220f07413c8d6cb404cc8c18bf5591bc159601660159054906101000a900460ff16604051611d359190614e88565b60405180910390a150565b611d486122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614611dd5576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401611dcc906150a5565b60405180910390fd5b60008054906101000a900473ffffffffffffffffffffffffffffffffffffffff16600160006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555060008060006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508042611e8391906152c1565b600281905550600073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a350565b6000600d60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054905092915050565b611f966122d3565b73ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1614612025576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161201c90615125565b60405180910390fd5b8073ffffffffffffffffffffffffffffffffffffffff16600360009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f80f15e9dbc60884fdb59fb8ed4fc48a9a689e028f055e893ed45ca5be67c5c8560405160405180910390a380600360006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b6120ed6122d3565b73ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff161461217a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612171906150a5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614156121ea576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016121e190614f45565b60405180910390fd5b8073ffffffffffffffffffffffffffffffffffffffff1660008054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff167f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e060405160405180910390a3806000806101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b600081836122b59190615317565b905092915050565b600081836122cb91906153a2565b905092915050565b600033905090565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff16141561234b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161234290614ee5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614156123bb576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016123b290615165565b60405180910390fd5b80600d60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055508173ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167f8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b9258360405161249991906151a5565b60405180910390a3505050565b600073ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612516576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161250d90614fc5565b60405180910390fd5b600073ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff161415612586576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161257d90615065565b60405180910390fd5b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff161415612617576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161260e90614fe5565b60405180910390fd5b6000811161265a576040517f08c379a0000000000000000000000000000000000000000000000000000000008152600401612651906150c5565b60405180910390fd5b600060019050600360149054906101000a900460ff161561267e57600090506127b2565b670c3663566a5800008211801561269b575061269984613107565b155b80156126ad57506126ab83613146565b155b156126ed576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016126e490615025565b60405180910390fd5b60006003670c3663566a5800006127049190615317565b118015612717575061271584613107565b155b8015612729575061272783613146565b155b801561273b5750612739836131dd565b155b156127b157600061274b84611433565b90506003670c3663566a5800006127629190615317565b838261276e91906152c1565b11156127af576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016127a690615105565b60405180910390fd5b505b5b600e60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16806128535750600e60008473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff165b1561285d57600090505b61286984848484613237565b6128758484848461326a565b50505050565b60008383111582906128c3576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016128ba9190614ea3565b60405180910390fd5b5082840390509392505050565b600081836128de91906152c1565b905092915050565b60008190508073ffffffffffffffffffffffffffffffffffffffff1663c45a01556040518163ffffffff1660e01b815260040160206040518083038186803b15801561293157600080fd5b505afa158015612945573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906129699190614783565b73ffffffffffffffffffffffffffffffffffffffff1663c9c65396308373ffffffffffffffffffffffffffffffffffffffff1663ad5c46486040518163ffffffff1660e01b815260040160206040518083038186803b1580156129cb57600080fd5b505afa1580156129df573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612a039190614783565b6040518363ffffffff1660e01b8152600401612a20929190614dfe565b602060405180830381600087803b158015612a3a57600080fd5b505af1158015612a4e573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190612a729190614783565b601660006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555080601560006101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff1602179055508173ffffffffffffffffffffffffffffffffffffffff167fc6b438e6a8a59579ce6a4406cbd203b740e0d47b458aae6596339bcd40c40d1560405160405180910390a25050565b6000806000612b47613614565b91509150612b5e81836122a790919063ffffffff16565b9250505090565b60008183612b739190615348565b905092915050565b612bef81600b6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff1615612da257612d3c82600c6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c6000600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168373ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef84604051612e2191906151a5565b60405180910390a3505050565b600080600080600080612e6261271061ffff16612e54898b612b6590919063ffffffff16565b6122a790919063ffffffff16565b90506000612e79828a6122bd90919063ffffffff16565b90506000612e85612b3a565b90506000612e9c828c612b6590919063ffffffff16565b90506000612eb38386612b6590919063ffffffff16565b90506000612eca82846122bd90919063ffffffff16565b905082818e87879a509a509a509a509a505050505050509295509295909350565b6000612eff612ef984611433565b83613982565b905092915050565b6000600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020541115612fdb57612f97600b60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054613099565b600c60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6001600f60008373ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060006101000a81548160ff0219169083151502179055506010819080600181540180825580915050600190039060005260206000200160009091909190916101000a81548173ffffffffffffffffffffffffffffffffffffffff021916908373ffffffffffffffffffffffffffffffffffffffff16021790555050565b60006004548211156130e0576040517f08c379a00000000000000000000000000000000000000000000000000000000081526004016130d790614f25565b60405180910390fd5b60006130ea612b3a565b90506130ff81846122a790919063ffffffff16565b915050919050565b600061311161177b565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16149050919050565b600061315061177b565b73ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614806131d65750600760009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16145b9050919050565b6000601660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16149050919050565b600360149054906101000a900460ff1661326457600061325630611433565b9050613262818661398f565b505b50505050565b60006132768584612eeb565b90508161328257600090505b60008060008060006132948887612e2e565b945094509450945094506132f085600b60008d73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600b60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1681526020019081526020016000208190555061338584600b60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156134b05761346c83600c60008d73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546122bd90919063ffffffff16565b600c60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b600f60008a73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156135985761355482600c60008c73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c60008b73ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6135a3888288613a48565b8873ffffffffffffffffffffffffffffffffffffffff168a73ffffffffffffffffffffffffffffffffffffffff167fddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef8460405161360091906151a5565b60405180910390a350505050505050505050565b600080600060045490506000670c3663566a580000905060005b60108054905081101561392e5782600b60006010848154811061367a577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054118061378e575081600c600060108481548110613726577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054115b156137ab57600454670c3663566a5800009450945050505061397e565b613861600b6000601084815481106137ec577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054846122bd90919063ffffffff16565b9250613919600c6000601084815481106138a4577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b9060005260206000200160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002054836122bd90919063ffffffff16565b9150808061392690615482565b91505061362e565b5060008114806139595750613956670c3663566a5800006004546122a790919063ffffffff16565b82105b1561397557600454670c3663566a58000093509350505061397e565b81819350935050505b9091565b6000600a54905092915050565b601754821061399e5760175491505b600060185483101590508080156139c15750601660159054906101000a900460ff165b80156139da5750601660149054906101000a900460ff16155b8015613a345750601660009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff1614155b15613a4357613a4283613a7a565b5b505050565b600081118015613a655750600360149054906101000a900460ff16155b15613a7557613a748383613b50565b5b505050565b6001601660146101000a81548160ff0219169083151502179055506000613aab6002836122a790919063ffffffff16565b90506000613ac282846122bd90919063ffffffff16565b90506000479050613ad283613df2565b6000613ae782476122bd90919063ffffffff16565b9050613af383826140b6565b7f17bbfb9a6069321b6ded73bd96327c9e6b7212a5cd51ff219cd61370acafb561848285604051613b269392919061521a565b60405180910390a1505050506000601660146101000a81548160ff02191690831515021790555050565b600360149054906101000a900460ff1615613b6a57613dee565b6000613b746141f7565b905060005b81811015613deb576000806000613b8f84614204565b509250925092506000821415613ba757505050613dd8565b60036005811115613be1577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613c1a577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613c3157613c2c87878487614337565b613dd4565b60016005811115613c6b577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613ca4577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613cbb57613cb6878784876143aa565b613dd3565b60006005811115613cf5577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613d2e577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613d3957613dd2565b600580811115613d72577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b836005811115613dab577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b1415613dc357613dbe878784848861440d565b613dd1565b613dd08787848488614421565b5b5b5b5b5050505b8080613de390615482565b915050613b79565b50505b5050565b6000600267ffffffffffffffff811115613e35577f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b604051908082528060200260200182016040528015613e635781602001602082028036833780820191505090505b5090503081600081518110613ea1577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b602002602001019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff1681525050601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663ad5c46486040518163ffffffff1660e01b815260040160206040518083038186803b158015613f4357600080fd5b505afa158015613f57573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190613f7b9190614783565b81600181518110613fb5577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b602002602001019073ffffffffffffffffffffffffffffffffffffffff16908173ffffffffffffffffffffffffffffffffffffffff168152505061401c30601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16846145f7565b601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663791ac9478360008430426040518663ffffffff1660e01b81526004016140809594939291906151c0565b600060405180830381600087803b15801561409a57600080fd5b505af11580156140ae573d6000803e3d6000fd5b505050505050565b6140e330601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff16846145f7565b6000806000601560009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1663f305d71985308860008061413461177b565b426040518863ffffffff1660e01b815260040161415696959493929190614e27565b6060604051808303818588803b15801561416f57600080fd5b505af1158015614183573d6000803e3d6000fd5b50505050506040513d601f19601f820116820180604052508101906141a89190614966565b925092509250476011819055507fd7f28048575eead8851d024ead087913957dfb4fd1a02b4d1573f5352a5a2be38383836040516141e89392919061521a565b60405180910390a15050505050565b6000600980549050905090565b600080600080600061421586614607565b6040518060800160405290816000820160009054906101000a900460ff16600581111561426b577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b60058111156142a3577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b8152602001600182015481526020016002820160009054906101000a900473ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001600382015481525050905080600001518160200151826040015183606001519450945094509450509193509193565b600061436461271061ffff166143568588612b6590919063ffffffff16565b6122a790919063ffffffff16565b9050600061437b8583612b6590919063ffffffff16565b9050614392816004546122bd90919063ffffffff16565b6004819055506143a283836146ab565b505050505050565b60006143d761271061ffff166143c98588612b6590919063ffffffff16565b6122a790919063ffffffff16565b905060006143ee8583612b6590919063ffffffff16565b90506143fb308383612b7b565b61440583836146ab565b505050505050565b61441a8585858585614421565b5050505050565b600061444e61271061ffff166144408689612b6590919063ffffffff16565b6122a790919063ffffffff16565b905060006144658683612b6590919063ffffffff16565b90506144b981600b60008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600b60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002081905550600f60008573ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff16815260200190815260200160002060009054906101000a900460ff16156145e4576145a082600c60008773ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020546128d090919063ffffffff16565b600c60008673ffffffffffffffffffffffffffffffffffffffff1673ffffffffffffffffffffffffffffffffffffffff168152602001908152602001600020819055505b6145ee83836146ab565b50505050505050565b6146028383836122db565b505050565b600080821015801561461d575060098054905082105b61465c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260040161465390615145565b60405180910390fd5b60098281548110614696577f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b90600052602060002090600402019050919050565b60006146b683614607565b90506146cf8282600301546128d090919063ffffffff16565b8160030181905550505050565b6000813590506146eb81615b95565b92915050565b60008151905061470081615b95565b92915050565b60008135905061471581615bac565b92915050565b60008135905061472a81615bc3565b92915050565b60008135905061473f81615bda565b92915050565b60008151905061475481615bda565b92915050565b60006020828403121561476c57600080fd5b600061477a848285016146dc565b91505092915050565b60006020828403121561479557600080fd5b60006147a3848285016146f1565b91505092915050565b6000602082840312156147be57600080fd5b60006147cc84828501614706565b91505092915050565b600080604083850312156147e857600080fd5b60006147f6858286016146dc565b9250506020614807858286016146dc565b9150509250929050565b60008060006060848603121561482657600080fd5b6000614834868287016146dc565b9350506020614845868287016146dc565b925050604061485686828701614730565b9150509250925092565b6000806040838503121561487357600080fd5b6000614881858286016146dc565b92505060206148928582860161471b565b9150509250929050565b600080604083850312156148af57600080fd5b60006148bd858286016146dc565b92505060206148ce85828601614730565b9150509250929050565b6000602082840312156148ea57600080fd5b60006148f88482850161471b565b91505092915050565b60006020828403121561491357600080fd5b600061492184828501614730565b91505092915050565b6000806040838503121561493d57600080fd5b600061494b85828601614730565b925050602061495c8582860161471b565b9150509250929050565b60008060006060848603121561497b57600080fd5b600061498986828701614745565b935050602061499a86828701614745565b92505060406149ab86828701614745565b9150509250925092565b60006149c183836149cd565b60208301905092915050565b6149d6816153d6565b82525050565b6149e5816153d6565b82525050565b60006149f68261527c565b614a00818561529f565b9350614a0b8361526c565b8060005b83811015614a3c578151614a2388826149b5565b9750614a2e83615292565b925050600181019050614a0f565b5085935050505092915050565b614a52816153fa565b82525050565b614a618161543d565b82525050565b6000614a7282615287565b614a7c81856152b0565b9350614a8c81856020860161544f565b614a9581615529565b840191505092915050565b6000614aad601c836152b0565b9150614ab88261553a565b602082019050919050565b6000614ad0602b836152b0565b9150614adb82615563565b604082019050919050565b6000614af3602c836152b0565b9150614afe826155b2565b604082019050919050565b6000614b16602a836152b0565b9150614b2182615601565b604082019050919050565b6000614b396026836152b0565b9150614b4482615650565b604082019050919050565b6000614b5c6017836152b0565b9150614b678261569f565b602082019050919050565b6000614b7f6028836152b0565b9150614b8a826156c8565b604082019050919050565b6000614ba26017836152b0565b9150614bad82615717565b602082019050919050565b6000614bc5602c836152b0565b9150614bd082615740565b604082019050919050565b6000614be8602c836152b0565b9150614bf38261578f565b604082019050919050565b6000614c0b601f836152b0565b9150614c16826157de565b602082019050919050565b6000614c2e6028836152b0565b9150614c3982615807565b604082019050919050565b6000614c516029836152b0565b9150614c5c82615856565b604082019050919050565b6000614c74602a836152b0565b9150614c7f826158a5565b604082019050919050565b6000614c976033836152b0565b9150614ca2826158f4565b604082019050919050565b6000614cba6020836152b0565b9150614cc582615943565b602082019050919050565b6000614cdd6029836152b0565b9150614ce88261596c565b604082019050919050565b6000614d006026836152b0565b9150614d0b826159bb565b604082019050919050565b6000614d23602d836152b0565b9150614d2e82615a0a565b604082019050919050565b6000614d466025836152b0565b9150614d5182615a59565b604082019050919050565b6000614d696033836152b0565b9150614d7482615aa8565b604082019050919050565b6000614d8c6029836152b0565b9150614d9782615af7565b604082019050919050565b6000614daf6028836152b0565b9150614dba82615b46565b604082019050919050565b614dce81615426565b82525050565b614ddd81615430565b82525050565b6000602082019050614df860008301846149dc565b92915050565b6000604082019050614e1360008301856149dc565b614e2060208301846149dc565b9392505050565b600060c082019050614e3c60008301896149dc565b614e496020830188614dc5565b614e566040830187614a58565b614e636060830186614a58565b614e7060808301856149dc565b614e7d60a0830184614dc5565b979650505050505050565b6000602082019050614e9d6000830184614a49565b92915050565b60006020820190508181036000830152614ebd8184614a67565b905092915050565b60006020820190508181036000830152614ede81614aa0565b9050919050565b60006020820190508181036000830152614efe81614ac3565b9050919050565b60006020820190508181036000830152614f1e81614ae6565b9050919050565b60006020820190508181036000830152614f3e81614b09565b9050919050565b60006020820190508181036000830152614f5e81614b2c565b9050919050565b60006020820190508181036000830152614f7e81614b4f565b9050919050565b60006020820190508181036000830152614f9e81614b72565b9050919050565b60006020820190508181036000830152614fbe81614b95565b9050919050565b60006020820190508181036000830152614fde81614bb8565b9050919050565b60006020820190508181036000830152614ffe81614bdb565b9050919050565b6000602082019050818103600083015261501e81614bfe565b9050919050565b6000602082019050818103600083015261503e81614c21565b9050919050565b6000602082019050818103600083015261505e81614c44565b9050919050565b6000602082019050818103600083015261507e81614c67565b9050919050565b6000602082019050818103600083015261509e81614c8a565b9050919050565b600060208201905081810360008301526150be81614cad565b9050919050565b600060208201905081810360008301526150de81614cd0565b9050919050565b600060208201905081810360008301526150fe81614cf3565b9050919050565b6000602082019050818103600083015261511e81614d16565b9050919050565b6000602082019050818103600083015261513e81614d39565b9050919050565b6000602082019050818103600083015261515e81614d5c565b9050919050565b6000602082019050818103600083015261517e81614d7f565b9050919050565b6000602082019050818103600083015261519e81614da2565b9050919050565b60006020820190506151ba6000830184614dc5565b92915050565b600060a0820190506151d56000830188614dc5565b6151e26020830187614a58565b81810360408301526151f481866149eb565b905061520360608301856149dc565b6152106080830184614dc5565b9695505050505050565b600060608201905061522f6000830186614dc5565b61523c6020830185614dc5565b6152496040830184614dc5565b949350505050565b60006020820190506152666000830184614dd4565b92915050565b6000819050602082019050919050565b600081519050919050565b600081519050919050565b6000602082019050919050565b600082825260208201905092915050565b600082825260208201905092915050565b60006152cc82615426565b91506152d783615426565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561530c5761530b6154cb565b5b828201905092915050565b600061532282615426565b915061532d83615426565b92508261533d5761533c6154fa565b5b828204905092915050565b600061535382615426565b915061535e83615426565b9250817fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0483118215151615615397576153966154cb565b5b828202905092915050565b60006153ad82615426565b91506153b883615426565b9250828210156153cb576153ca6154cb565b5b828203905092915050565b60006153e182615406565b9050919050565b60006153f382615406565b9050919050565b60008115159050919050565b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b6000819050919050565b600060ff82169050919050565b600061544882615426565b9050919050565b60005b8381101561546d578082015181840152602081019050615452565b8381111561547c576000848401525b50505050565b600061548d82615426565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8214156154c0576154bf6154cb565b5b600182019050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601260045260246000fd5b6000601f19601f8301169050919050565b7f54686520636f6e7472616374206973207374696c6c206c6f636b656400000000600082015250565b7f42617365526669546f6b656e3a20617070726f76652066726f6d20746865207a60008201527f65726f2061646472657373000000000000000000000000000000000000000000602082015250565b7f4f6e6c79207468652070726576696f7573206f776e65722063616e20756e6c6f60008201527f636b206f6e776572736869700000000000000000000000000000000000000000602082015250565b7f416d6f756e74206d757374206265206c657373207468616e20746f74616c207260008201527f65666c656374696f6e7300000000000000000000000000000000000000000000602082015250565b7f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160008201527f6464726573730000000000000000000000000000000000000000000000000000602082015250565b7f4163636f756e74206973206e6f7420696e636c75646564000000000000000000600082015250565b7f42617365526669546f6b656e3a206275726e2066726f6d20746865206275726e60008201527f2061646472657373000000000000000000000000000000000000000000000000602082015250565b7f4163636f756e74206973206e6f74206578636c75646564000000000000000000600082015250565b7f42617365526669546f6b656e3a207472616e736665722066726f6d207468652060008201527f7a65726f20616464726573730000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a207472616e736665722066726f6d207468652060008201527f6275726e20616464726573730000000000000000000000000000000000000000602082015250565b7f416d6f756e74206d757374206265206c657373207468616e20737570706c7900600082015250565b7f5472616e7366657220616d6f756e74206578636565647320746865206d61785460008201527f78416d6f756e742e000000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a206275726e20616d6f756e742065786365656460008201527f732062616c616e63650000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a207472616e7366657220746f20746865207a6560008201527f726f206164647265737300000000000000000000000000000000000000000000602082015250565b7f43616e6e6f7420776974686472617720746865204554482062616c616e63652060008201527f746f20746865207a65726f206164647265737300000000000000000000000000602082015250565b7f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572600082015250565b7f5472616e7366657220616d6f756e74206d75737420626520677265617465722060008201527f7468616e207a65726f0000000000000000000000000000000000000000000000602082015250565b7f546865204554482062616c616e6365206d75737420626520677265617465722060008201527f7468616e20300000000000000000000000000000000000000000000000000000602082015250565b7f4e65772062616c616e636520776f756c642065786365656420746865206d617860008201527f57616c6c657442616c616e636500000000000000000000000000000000000000602082015250565b7f4d616e61676561626c653a2063616c6c6572206973206e6f7420746865206d6160008201527f6e61676572000000000000000000000000000000000000000000000000000000602082015250565b7f4665657353657474696e67732e5f6765744665655374727563743a204665652060008201527f696e646578206f7574206f6620626f756e647300000000000000000000000000602082015250565b7f42617365526669546f6b656e3a20617070726f766520746f20746865207a657260008201527f6f20616464726573730000000000000000000000000000000000000000000000602082015250565b7f42617365526669546f6b656e3a206275726e2066726f6d20746865207a65726f60008201527f2061646472657373000000000000000000000000000000000000000000000000602082015250565b615b9e816153d6565b8114615ba957600080fd5b50565b615bb5816153e8565b8114615bc057600080fd5b50565b615bcc816153fa565b8114615bd757600080fd5b50565b615be381615426565b8114615bee57600080fd5b5056fe45524332303a207472616e7366657220616d6f756e74206578636565647320616c6c6f77616e636545524332303a2064656372656173656420616c6c6f77616e63652062656c6f77207a65726fa26469706673582212203e43835e1879172c1066111b820887ae4055bbb1e1a018e20e8caed9e8b4de8064736f6c63430008040033