Contract Address Details

0xC8E6b94B121dF6afa3f698df2c51F8B779A02170

Contract Name
SolarDistributor
Creator
0x87c30f–b0c580 at 0xba59af–439c16
Balance
0 ASTR ( )
Tokens
Fetching tokens...
Transactions
12,488 Transactions
Transfers
37,925 Transfers
Gas Used
1,419,560,250
Last Balance Update
1355038
Contract name:
SolarDistributor




Optimization enabled
true
Compiler version
v0.8.9+commit.e5eed63a




Optimization runs
200
EVM Version
default




Verified at
2022-04-06T19:03:36.569766Z

Constructor Arguments

0000000000000000000000005d1af739fd538d363fd61a59d3cbb7b70784a3ac000000000000000000000000000000000000000000000000000000000000001e

Arg [0] (address) : 0x5d1af739fd538d363fd61a59d3cbb7b70784a3ac
Arg [1] (uint256) : 30

              

Contract source code

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;

/**
 * @dev Interface of the ERC20 standard as defined in the EIP.
 */
interface IERC20 {
    /**
     * @dev Returns the amount of tokens in existence.
     */
    function totalSupply() external view returns (uint256);

    /**
     * @dev Returns the amount of tokens owned by `account`.
     */
    function balanceOf(address account) external view returns (uint256);

    /**
     * @dev Moves `amount` tokens from the caller's account to `recipient`.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * Emits a {Transfer} event.
     */
    function transfer(address recipient, uint256 amount) external returns (bool);

    /**
     * @dev Returns the remaining number of tokens that `spender` will be
     * allowed to spend on behalf of `owner` through {transferFrom}. This is
     * zero by default.
     *
     * This value changes when {approve} or {transferFrom} are called.
     */
    function allowance(address owner, address spender) external view returns (uint256);

    /**
     * @dev Sets `amount` as the allowance of `spender` over the caller's tokens.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * IMPORTANT: Beware that changing an allowance with this method brings the risk
     * that someone may use both the old and the new allowance by unfortunate
     * transaction ordering. One possible solution to mitigate this race
     * condition is to first reduce the spender's allowance to 0 and set the
     * desired value afterwards:
     * https://github.com/ethereum/EIPs/issues/20#issuecomment-263524729
     *
     * Emits an {Approval} event.
     */
    function approve(address spender, uint256 amount) external returns (bool);

    /**
     * @dev Moves `amount` tokens from `sender` to `recipient` using the
     * allowance mechanism. `amount` is then deducted from the caller's
     * allowance.
     *
     * Returns a boolean value indicating whether the operation succeeded.
     *
     * Emits a {Transfer} event.
     */
    function transferFrom(
        address sender,
        address recipient,
        uint256 amount
    ) external returns (bool);

    /**
     * @dev Emitted when `value` tokens are moved from one account (`from`) to
     * another (`to`).
     *
     * Note that `value` may be zero.
     */
    event Transfer(address indexed from, address indexed to, uint256 value);

    /**
     * @dev Emitted when the allowance of a `spender` for an `owner` is set by
     * a call to {approve}. `value` is the new allowance.
     */
    event Approval(address indexed owner, address indexed spender, uint256 value);
}


/**
 * @dev Collection of functions related to the address type
 */
library Address {
    /**
     * @dev Returns true if `account` is a contract.
     *
     * [IMPORTANT]
     * ====
     * It is unsafe to assume that an address for which this function returns
     * false is an externally-owned account (EOA) and not a contract.
     *
     * Among others, `isContract` will return false for the following
     * types of addresses:
     *
     *  - an externally-owned account
     *  - a contract in construction
     *  - an address where a contract will be created
     *  - an address where a contract lived, but was destroyed
     * ====
     */
    function isContract(address account) internal view returns (bool) {
        // This method relies on extcodesize, which returns 0 for contracts in
        // construction, since the code is only stored at the end of the
        // constructor execution.

        uint256 size;
        assembly {
            size := extcodesize(account)
        }
        return size > 0;
    }

    /**
     * @dev Replacement for Solidity's `transfer`: sends `amount` wei to
     * `recipient`, forwarding all available gas and reverting on errors.
     *
     * https://eips.ethereum.org/EIPS/eip-1884[EIP1884] increases the gas cost
     * of certain opcodes, possibly making contracts go over the 2300 gas limit
     * imposed by `transfer`, making them unable to receive funds via
     * `transfer`. {sendValue} removes this limitation.
     *
     * https://diligence.consensys.net/posts/2019/09/stop-using-soliditys-transfer-now/[Learn more].
     *
     * IMPORTANT: because control is transferred to `recipient`, care must be
     * taken to not create reentrancy vulnerabilities. Consider using
     * {ReentrancyGuard} or the
     * https://solidity.readthedocs.io/en/v0.5.11/security-considerations.html#use-the-checks-effects-interactions-pattern[checks-effects-interactions pattern].
     */
    function sendValue(address payable recipient, uint256 amount) internal {
        require(address(this).balance >= amount, "Address: insufficient balance");

        (bool success, ) = recipient.call{value: amount}("");
        require(success, "Address: unable to send value, recipient may have reverted");
    }

    /**
     * @dev Performs a Solidity function call using a low level `call`. A
     * plain `call` is an unsafe replacement for a function call: use this
     * function instead.
     *
     * If `target` reverts with a revert reason, it is bubbled up by this
     * function (like regular Solidity function calls).
     *
     * Returns the raw returned data. To convert to the expected return value,
     * use https://solidity.readthedocs.io/en/latest/units-and-global-variables.html?highlight=abi.decode#abi-encoding-and-decoding-functions[`abi.decode`].
     *
     * Requirements:
     *
     * - `target` must be a contract.
     * - calling `target` with `data` must not revert.
     *
     * _Available since v3.1._
     */
    function functionCall(address target, bytes memory data) internal returns (bytes memory) {
        return functionCall(target, data, "Address: low-level call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`], but with
     * `errorMessage` as a fallback revert reason when `target` reverts.
     *
     * _Available since v3.1._
     */
    function functionCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal returns (bytes memory) {
        return functionCallWithValue(target, data, 0, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but also transferring `value` wei to `target`.
     *
     * Requirements:
     *
     * - the calling contract must have an ETH balance of at least `value`.
     * - the called Solidity function must be `payable`.
     *
     * _Available since v3.1._
     */
    function functionCallWithValue(
        address target,
        bytes memory data,
        uint256 value
    ) internal returns (bytes memory) {
        return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
    }

    /**
     * @dev Same as {xref-Address-functionCallWithValue-address-bytes-uint256-}[`functionCallWithValue`], but
     * with `errorMessage` as a fallback revert reason when `target` reverts.
     *
     * _Available since v3.1._
     */
    function functionCallWithValue(
        address target,
        bytes memory data,
        uint256 value,
        string memory errorMessage
    ) internal returns (bytes memory) {
        require(address(this).balance >= value, "Address: insufficient balance for call");
        require(isContract(target), "Address: call to non-contract");

        (bool success, bytes memory returndata) = target.call{value: value}(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but performing a static call.
     *
     * _Available since v3.3._
     */
    function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
        return functionStaticCall(target, data, "Address: low-level static call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
     * but performing a static call.
     *
     * _Available since v3.3._
     */
    function functionStaticCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal view returns (bytes memory) {
        require(isContract(target), "Address: static call to non-contract");

        (bool success, bytes memory returndata) = target.staticcall(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-}[`functionCall`],
     * but performing a delegate call.
     *
     * _Available since v3.4._
     */
    function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
        return functionDelegateCall(target, data, "Address: low-level delegate call failed");
    }

    /**
     * @dev Same as {xref-Address-functionCall-address-bytes-string-}[`functionCall`],
     * but performing a delegate call.
     *
     * _Available since v3.4._
     */
    function functionDelegateCall(
        address target,
        bytes memory data,
        string memory errorMessage
    ) internal returns (bytes memory) {
        require(isContract(target), "Address: delegate call to non-contract");

        (bool success, bytes memory returndata) = target.delegatecall(data);
        return _verifyCallResult(success, returndata, errorMessage);
    }

    function _verifyCallResult(
        bool success,
        bytes memory returndata,
        string memory errorMessage
    ) private pure returns (bytes memory) {
        if (success) {
            return returndata;
        } else {
            // Look for revert reason and bubble it up if present
            if (returndata.length > 0) {
                // The easiest way to bubble the revert reason is using memory via assembly

                assembly {
                    let returndata_size := mload(returndata)
                    revert(add(32, returndata), returndata_size)
                }
            } else {
                revert(errorMessage);
            }
        }
    }
}


/**
 * @title SafeERC20
 * @dev Wrappers around ERC20 operations that throw on failure (when the token
 * contract returns false). Tokens that return no value (and instead revert or
 * throw on failure) are also supported, non-reverting calls are assumed to be
 * successful.
 * To use this library you can add a `using SafeERC20 for IERC20;` statement to your contract,
 * which allows you to call the safe operations as `token.safeTransfer(...)`, etc.
 */
library SafeERC20 {
    using Address for address;

    function safeTransfer(
        IERC20 token,
        address to,
        uint256 value
    ) internal {
        _callOptionalReturn(token, abi.encodeWithSelector(token.transfer.selector, to, value));
    }

    function safeTransferFrom(
        IERC20 token,
        address from,
        address to,
        uint256 value
    ) internal {
        _callOptionalReturn(token, abi.encodeWithSelector(token.transferFrom.selector, from, to, value));
    }

    /**
     * @dev Deprecated. This function has issues similar to the ones found in
     * {IERC20-approve}, and its usage is discouraged.
     *
     * Whenever possible, use {safeIncreaseAllowance} and
     * {safeDecreaseAllowance} instead.
     */
    function safeApprove(
        IERC20 token,
        address spender,
        uint256 value
    ) internal {
        // safeApprove should only be called when setting an initial allowance,
        // or when resetting it to zero. To increase and decrease it, use
        // 'safeIncreaseAllowance' and 'safeDecreaseAllowance'
        require(
            (value == 0) || (token.allowance(address(this), spender) == 0),
            "SafeERC20: approve from non-zero to non-zero allowance"
        );
        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value));
    }

    function safeIncreaseAllowance(
        IERC20 token,
        address spender,
        uint256 value
    ) internal {
        uint256 newAllowance = token.allowance(address(this), spender) + value;
        _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));
    }

    function safeDecreaseAllowance(
        IERC20 token,
        address spender,
        uint256 value
    ) internal {
        unchecked {
            uint256 oldAllowance = token.allowance(address(this), spender);
            require(oldAllowance >= value, "SafeERC20: decreased allowance below zero");
            uint256 newAllowance = oldAllowance - value;
            _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, newAllowance));
        }
    }

    /**
     * @dev Imitates a Solidity high-level call (i.e. a regular function call to a contract), relaxing the requirement
     * on the return value: the return value is optional (but if data is returned, it must not be false).
     * @param token The token targeted by the call.
     * @param data The call data (encoded using abi.encode or one of its variants).
     */
    function _callOptionalReturn(IERC20 token, bytes memory data) private {
        // We need to perform a low level call here, to bypass Solidity's return data size checking mechanism, since
        // we're implementing it ourselves. We use {Address.functionCall} to perform this call, which verifies that
        // the target address contains contract code and also asserts for success in the low-level call.

        bytes memory returndata = address(token).functionCall(data, "SafeERC20: low-level call failed");
        if (returndata.length > 0) {
            // Return data is optional
            require(abi.decode(returndata, (bool)), "SafeERC20: ERC20 operation did not succeed");
        }
    }
}


/*
 * @dev Provides information about the current execution context, including the
 * sender of the transaction and its data. While these are generally available
 * via msg.sender and msg.data, they should not be accessed in such a direct
 * manner, since when dealing with meta-transactions the account sending and
 * paying for execution may not be the actual sender (as far as an application
 * is concerned).
 *
 * This contract is only required for intermediate, library-like contracts.
 */
abstract contract Context {
    function _msgSender() internal view virtual returns (address) {
        return msg.sender;
    }

    function _msgData() internal view virtual returns (bytes calldata) {
        return msg.data;
    }
}



/**
 * @dev Contract module which provides a basic access control mechanism, where
 * there is an account (an owner) that can be granted exclusive access to
 * specific functions.
 *
 * By default, the owner account will be the one that deploys the contract. This
 * can later be changed with {transferOwnership}.
 *
 * This module is used through inheritance. It will make available the modifier
 * `onlyOwner`, which can be applied to your functions to restrict their use to
 * the owner.
 */
abstract contract Ownable is Context {
    address private _owner;

    event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);

    /**
     * @dev Initializes the contract setting the deployer as the initial owner.
     */
    constructor() {
        _setOwner(_msgSender());
    }

    /**
     * @dev Returns the address of the current owner.
     */
    function owner() public view virtual returns (address) {
        return _owner;
    }

    /**
     * @dev Throws if called by any account other than the owner.
     */
    modifier onlyOwner() {
        require(owner() == _msgSender(), "Ownable: caller is not the owner");
        _;
    }

    /**
     * @dev Leaves the contract without owner. It will not be possible to call
     * `onlyOwner` functions anymore. Can only be called by the current owner.
     *
     * NOTE: Renouncing ownership will leave the contract without an owner,
     * thereby removing any functionality that is only available to the owner.
     */
    function renounceOwnership() public virtual onlyOwner {
        _setOwner(address(0));
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`).
     * Can only be called by the current owner.
     */
    function transferOwnership(address newOwner) public virtual onlyOwner {
        require(newOwner != address(0), "Ownable: new owner is the zero address");
        _setOwner(newOwner);
    }

    function _setOwner(address newOwner) private {
        address oldOwner = _owner;
        _owner = newOwner;
        emit OwnershipTransferred(oldOwner, newOwner);
    }
}



/**
 * @dev Contract module that helps prevent reentrant calls to a function.
 *
 * Inheriting from `ReentrancyGuard` will make the {nonReentrant} modifier
 * available, which can be applied to functions to make sure there are no nested
 * (reentrant) calls to them.
 *
 * Note that because there is a single `nonReentrant` guard, functions marked as
 * `nonReentrant` may not call one another. This can be worked around by making
 * those functions `private`, and then adding `external` `nonReentrant` entry
 * points to them.
 *
 * TIP: If you would like to learn more about reentrancy and alternative ways
 * to protect against it, check out our blog post
 * https://blog.openzeppelin.com/reentrancy-after-istanbul/[Reentrancy After Istanbul].
 */
abstract contract ReentrancyGuard {
    // Booleans are more expensive than uint256 or any type that takes up a full
    // word because each write operation emits an extra SLOAD to first read the
    // slot's contents, replace the bits taken up by the boolean, and then write
    // back. This is the compiler's defense against contract upgrades and
    // pointer aliasing, and it cannot be disabled.

    // The values being non-zero value makes deployment a bit more expensive,
    // but in exchange the refund on every call to nonReentrant will be lower in
    // amount. Since refunds are capped to a percentage of the total
    // transaction's gas, it is best to keep them low in cases like this one, to
    // increase the likelihood of the full refund coming into effect.
    uint256 private constant _NOT_ENTERED = 1;
    uint256 private constant _ENTERED = 2;

    uint256 private _status;

    constructor() {
        _status = _NOT_ENTERED;
    }

    /**
     * @dev Prevents a contract from calling itself, directly or indirectly.
     * Calling a `nonReentrant` function from another `nonReentrant`
     * function is not supported. It is possible to prevent this from happening
     * by making the `nonReentrant` function external, and make it call a
     * `private` function that does the actual work.
     */
    modifier nonReentrant() {
        // On the first call to nonReentrant, _notEntered will be true
        require(_status != _ENTERED, "ReentrancyGuard: reentrant call");

        // Any calls to nonReentrant after this point will fail
        _status = _ENTERED;

        _;

        // By storing the original value once again, a refund is triggered (see
        // https://eips.ethereum.org/EIPS/eip-2200)
        _status = _NOT_ENTERED;
    }
}


// CAUTION
// This version of SafeMath should only be used with Solidity 0.8 or later,
// because it relies on the compiler's built in overflow checks.

/**
 * @dev Wrappers over Solidity's arithmetic operations.
 *
 * NOTE: `SafeMath` is no longer needed starting with Solidity 0.8. The compiler
 * now has built in overflow checking.
 */
library SafeMath {
    /**
     * @dev Returns the addition of two unsigned integers, with an overflow flag.
     *
     * _Available since v3.4._
     */
    function tryAdd(uint256 a, uint256 b) internal pure returns (bool, uint256) {
        unchecked {
            uint256 c = a + b;
            if (c < a) return (false, 0);
            return (true, c);
        }
    }

    /**
     * @dev Returns the substraction of two unsigned integers, with an overflow flag.
     *
     * _Available since v3.4._
     */
    function trySub(uint256 a, uint256 b) internal pure returns (bool, uint256) {
        unchecked {
            if (b > a) return (false, 0);
            return (true, a - b);
        }
    }

    /**
     * @dev Returns the multiplication of two unsigned integers, with an overflow flag.
     *
     * _Available since v3.4._
     */
    function tryMul(uint256 a, uint256 b) internal pure returns (bool, uint256) {
        unchecked {
            // Gas optimization: this is cheaper than requiring 'a' not being zero, but the
            // benefit is lost if 'b' is also tested.
            // See: https://github.com/OpenZeppelin/openzeppelin-contracts/pull/522
            if (a == 0) return (true, 0);
            uint256 c = a * b;
            if (c / a != b) return (false, 0);
            return (true, c);
        }
    }

    /**
     * @dev Returns the division of two unsigned integers, with a division by zero flag.
     *
     * _Available since v3.4._
     */
    function tryDiv(uint256 a, uint256 b) internal pure returns (bool, uint256) {
        unchecked {
            if (b == 0) return (false, 0);
            return (true, a / b);
        }
    }

    /**
     * @dev Returns the remainder of dividing two unsigned integers, with a division by zero flag.
     *
     * _Available since v3.4._
     */
    function tryMod(uint256 a, uint256 b) internal pure returns (bool, uint256) {
        unchecked {
            if (b == 0) return (false, 0);
            return (true, a % b);
        }
    }

    /**
     * @dev Returns the addition of two unsigned integers, reverting on
     * overflow.
     *
     * Counterpart to Solidity's `+` operator.
     *
     * Requirements:
     *
     * - Addition cannot overflow.
     */
    function add(uint256 a, uint256 b) internal pure returns (uint256) {
        return a + b;
    }

    /**
     * @dev Returns the subtraction of two unsigned integers, reverting on
     * overflow (when the result is negative).
     *
     * Counterpart to Solidity's `-` operator.
     *
     * Requirements:
     *
     * - Subtraction cannot overflow.
     */
    function sub(uint256 a, uint256 b) internal pure returns (uint256) {
        return a - b;
    }

    /**
     * @dev Returns the multiplication of two unsigned integers, reverting on
     * overflow.
     *
     * Counterpart to Solidity's `*` operator.
     *
     * Requirements:
     *
     * - Multiplication cannot overflow.
     */
    function mul(uint256 a, uint256 b) internal pure returns (uint256) {
        return a * b;
    }

    /**
     * @dev Returns the integer division of two unsigned integers, reverting on
     * division by zero. The result is rounded towards zero.
     *
     * Counterpart to Solidity's `/` operator.
     *
     * Requirements:
     *
     * - The divisor cannot be zero.
     */
    function div(uint256 a, uint256 b) internal pure returns (uint256) {
        return a / b;
    }

    /**
     * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
     * reverting when dividing by zero.
     *
     * Counterpart to Solidity's `%` operator. This function uses a `revert`
     * opcode (which leaves remaining gas untouched) while Solidity uses an
     * invalid opcode to revert (consuming all remaining gas).
     *
     * Requirements:
     *
     * - The divisor cannot be zero.
     */
    function mod(uint256 a, uint256 b) internal pure returns (uint256) {
        return a % b;
    }

    /**
     * @dev Returns the subtraction of two unsigned integers, reverting with custom message on
     * overflow (when the result is negative).
     *
     * CAUTION: This function is deprecated because it requires allocating memory for the error
     * message unnecessarily. For custom revert reasons use {trySub}.
     *
     * Counterpart to Solidity's `-` operator.
     *
     * Requirements:
     *
     * - Subtraction cannot overflow.
     */
    function sub(
        uint256 a,
        uint256 b,
        string memory errorMessage
    ) internal pure returns (uint256) {
        unchecked {
            require(b <= a, errorMessage);
            return a - b;
        }
    }

    /**
     * @dev Returns the integer division of two unsigned integers, reverting with custom message on
     * division by zero. The result is rounded towards zero.
     *
     * Counterpart to Solidity's `/` operator. Note: this function uses a
     * `revert` opcode (which leaves remaining gas untouched) while Solidity
     * uses an invalid opcode to revert (consuming all remaining gas).
     *
     * Requirements:
     *
     * - The divisor cannot be zero.
     */
    function div(
        uint256 a,
        uint256 b,
        string memory errorMessage
    ) internal pure returns (uint256) {
        unchecked {
            require(b > 0, errorMessage);
            return a / b;
        }
    }

    /**
     * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
     * reverting with custom message when dividing by zero.
     *
     * CAUTION: This function is deprecated because it requires allocating memory for the error
     * message unnecessarily. For custom revert reasons use {tryMod}.
     *
     * Counterpart to Solidity's `%` operator. This function uses a `revert`
     * opcode (which leaves remaining gas untouched) while Solidity uses an
     * invalid opcode to revert (consuming all remaining gas).
     *
     * Requirements:
     *
     * - The divisor cannot be zero.
     */
    function mod(
        uint256 a,
        uint256 b,
        string memory errorMessage
    ) internal pure returns (uint256) {
        unchecked {
            require(b > 0, errorMessage);
            return a % b;
        }
    }
}

/**
 * @dev Interface of the ERC20 standard as defined in the EIP.
 */
interface ISolarERC20 is IERC20 {
    function mint(address to, uint256 amount) external;
}


contract SolarDistributor is Ownable, ReentrancyGuard {

    // remember to change for mainnet deploy
    address constant _trustedForwarder = 0xc128B8E142a70e16547484d50b5353478103Db99; //TRUSTED FORWARDER

    using SafeMath for uint256;
    using SafeERC20 for IERC20;

    // Info of each user.
    struct UserInfo {
        uint256 amount; // How many LP tokens the user has provided.
        uint256 rewardDebt; // Reward debt. See explanation below.
        uint256 rewardLockedUp; // Reward locked up.
        uint256 nextHarvestUntil; // When can the user harvest again.
    }

    // Info of each pool.
    struct PoolInfo {
        IERC20 lpToken; // Address of LP token contract.
        uint256 allocPoint; // How many allocation points assigned to this pool. Solar to distribute per block.
        uint256 lastRewardBlock; // Last block number that Solar distribution occurs.
        uint256 accSolarPerShare; // Accumulated Solar per share, times 1e12. See below.
        uint16 depositFeeBP; // Deposit fee in basis points
        uint256 harvestInterval; // Harvest interval in seconds
        uint256 totalLp; // Total token in Pool
    }

    ISolarERC20 public solar;

    // The operator can only update EmissionRate and AllocPoint to protect tokenomics
    //i.e some wrong setting and a pools get too much allocation accidentally
    address private _operator;

    // Dev address.
    address public devAddress;

    // Deposit Fee address
    address public feeAddress;

    // Solar tokens created per block
    uint256 public solarPerBlock;

    // Max harvest interval: 14 days
    uint256 public constant MAXIMUM_HARVEST_INTERVAL = 14 days;

    // Maximum deposit fee rate: 10%
    uint16 public constant MAXIMUM_DEPOSIT_FEE_RATE = 1000;

    // Info of each pool
    PoolInfo[] public poolInfo;

    // Info of each user that stakes LP tokens.
    mapping(uint256 => mapping(address => UserInfo)) public userInfo;

    // Total allocation points. Must be the sum of all allocation points in all pools.
    uint256 public totalAllocPoint = 0;

    // The block number when Solar mining starts.
    uint256 public startBlock;

    // Total locked up rewards
    uint256 public totalLockedUpRewards;

    // Total Solar in Solar Pools (can be multiple pools)
    uint256 public totalSolarInPools = 0;

    // Control support for EIP-2771 Meta Transactions
    bool public metaTxnsEnabled = false;


    event Deposit(address indexed user, uint256 indexed pid, uint256 amount);
    event Withdraw(address indexed user, uint256 indexed pid, uint256 amount);
    event EmergencyWithdraw(address indexed user, uint256 indexed pid, uint256 amount);
    event EmissionRateUpdated(address indexed caller, uint256 previousAmount, uint256 newAmount);
    event RewardLockedUp(address indexed user, uint256 indexed pid, uint256 amountLockedUp);
    event OperatorTransferred(address indexed previousOperator, address indexed newOperator);
    event DevAddressChanged(address indexed caller, address oldAddress, address newAddress);
    event FeeAddressChanged(address indexed caller, address oldAddress, address newAddress);
    event AllocPointsUpdated(address indexed caller, uint256 previousAmount, uint256 newAmount);
    event MetaTxnsEnabled(address indexed caller);
    event MetaTxnsDisabled(address indexed caller);

    modifier onlyOperator() {
        require(_operator == msg.sender, "Operator: caller is not the operator");
        _;
    }

    constructor(
        ISolarERC20 _solar,
        uint256 _solarPerBlock
    ) {
        //StartBlock always many years later from contract construct, will be set later in StartFarming function
        startBlock = block.number + (10 * 365 * 24 * 60 * 60);

        solar = _solar;
        solarPerBlock = _solarPerBlock;

        devAddress = msg.sender;
        feeAddress = msg.sender;
        _operator = msg.sender;
        emit OperatorTransferred(address(0), _operator);
    }

    function isTrustedForwarder(address forwarder) public view virtual returns (bool) {
        return metaTxnsEnabled && forwarder == _trustedForwarder;
    }

    function _msgSender() internal view virtual override returns (address sender) {
        if (isTrustedForwarder(msg.sender)) {
            // The assembly code is more direct than the Solidity version using `abi.decode`.
            assembly {
                sender := shr(96, calldataload(sub(calldatasize(), 20)))
            }
        } else {
            return super._msgSender();
        }
    }

    function _msgData() internal view virtual override returns (bytes calldata) {
        if (isTrustedForwarder(msg.sender)) {
            return msg.data[:msg.data.length - 20];
        } else {
            return super._msgData();
        }
    }

    function operator() public view returns (address) {
        return _operator;
    }

    // Return reward multiplier over the given _from to _to block.
    function getMultiplier(uint256 _from, uint256 _to) public pure returns (uint256) {
        return _to.sub(_from);
    }

    function transferOperator(address newOperator) public onlyOperator {
        require(newOperator != address(0), "TransferOperator: new operator is the zero address");
        emit OperatorTransferred(_operator, newOperator);
        _operator = newOperator;
    }

    // Set farming start, can call only once
    function startFarming() public onlyOwner {
        require(block.number < startBlock, "Error::Farm started already");

        uint256 length = poolInfo.length;
        for (uint256 pid = 0; pid < length; ++pid) {
            PoolInfo storage pool = poolInfo[pid];
            pool.lastRewardBlock = block.number;
        }

        startBlock = block.number;
    }

    function poolLength() external view returns (uint256) {
        return poolInfo.length;
    }

    // Add a new lp to the pool. Can only be called by the owner.
    // Can add multiple pool with same lp token without messing up rewards, because each pool's balance is tracked using its own totalLp
    function add(
        uint256 _allocPoint,
        IERC20 _lpToken,
        uint16 _depositFeeBP,
        uint256 _harvestInterval,
        bool _withUpdate
    ) public onlyOwner {
        require(_depositFeeBP <= MAXIMUM_DEPOSIT_FEE_RATE, "add: deposit fee too high");
        require(_harvestInterval <= MAXIMUM_HARVEST_INTERVAL, "add: invalid harvest interval");
        if (_withUpdate) {
            massUpdatePools();
        }
        uint256 lastRewardBlock = block.number > startBlock ? block.number : startBlock;
        totalAllocPoint = totalAllocPoint.add(_allocPoint);
        poolInfo.push(PoolInfo({lpToken: _lpToken, allocPoint: _allocPoint, lastRewardBlock: lastRewardBlock, accSolarPerShare: 0, depositFeeBP: _depositFeeBP, harvestInterval: _harvestInterval, totalLp: 0}));
    }

    // Update the given pool's Solar allocation point and deposit fee. Can only be called by the owner.
    function set(
        uint256 _pid,
        uint256 _allocPoint,
        uint16 _depositFeeBP,
        uint256 _harvestInterval,
        bool _withUpdate
    ) public onlyOwner {
        require(_depositFeeBP <= MAXIMUM_DEPOSIT_FEE_RATE, "set: deposit fee too high");
        require(_harvestInterval <= MAXIMUM_HARVEST_INTERVAL, "set: invalid harvest interval");
        if (_withUpdate) {
            massUpdatePools();
        }
        totalAllocPoint = totalAllocPoint.sub(poolInfo[_pid].allocPoint).add(_allocPoint);
        poolInfo[_pid].allocPoint = _allocPoint;
        poolInfo[_pid].depositFeeBP = _depositFeeBP;
        poolInfo[_pid].harvestInterval = _harvestInterval;
    }

    // View function to see pending Solar on frontend.
    function pendingSolar(uint256 _pid, address _user) external view returns (uint256) {
        PoolInfo storage pool = poolInfo[_pid];
        UserInfo storage user = userInfo[_pid][_user];
        uint256 accSolarPerShare = pool.accSolarPerShare;
        uint256 lpSupply = pool.lpToken.balanceOf(address(this));

        if (block.number > pool.lastRewardBlock && lpSupply != 0) {
            uint256 multiplier = getMultiplier(pool.lastRewardBlock, block.number);
            uint256 solarReward = multiplier.mul(solarPerBlock).mul(pool.allocPoint).div(totalAllocPoint);
            accSolarPerShare = accSolarPerShare.add(solarReward.mul(1e12).div(lpSupply));
        }

        uint256 pending = user.amount.mul(accSolarPerShare).div(1e12).sub(user.rewardDebt);
        return pending.add(user.rewardLockedUp);
    }

    // View function to see if user can harvest Solar.
    function canHarvest(uint256 _pid, address _user) public view returns (bool) {
        UserInfo storage user = userInfo[_pid][_user];
        return block.number >= startBlock && block.timestamp >= user.nextHarvestUntil;
    }

    // Update reward vairables for all pools. Be careful of gas spending!
    function massUpdatePools() public {
        uint256 length = poolInfo.length;
        for (uint256 pid = 0; pid < length; ++pid) {
            updatePool(pid);
        }
    }

    // Update reward variables of the given pool to be up-to-date.
    function updatePool(uint256 _pid) public {
        PoolInfo storage pool = poolInfo[_pid];
        if (block.number <= pool.lastRewardBlock) {
            return;
        }

        uint256 lpSupply = pool.totalLp;
        if (lpSupply == 0 || pool.allocPoint == 0) {
            pool.lastRewardBlock = block.number;
            return;
        }

        uint256 multiplier = getMultiplier(pool.lastRewardBlock, block.number);
        uint256 solarReward =
            multiplier.mul(solarPerBlock).mul(pool.allocPoint).div(
                totalAllocPoint
            );

        solar.mint(devAddress, solarReward.div(10));
        solar.mint(address(this), solarReward);

        pool.accSolarPerShare = pool.accSolarPerShare.add(
            solarReward.mul(1e12).div(pool.totalLp)
        );
        pool.lastRewardBlock = block.number;


    }

    // Deposit LP tokens to MasterChef for Solar allocation.
    function deposit(uint256 _pid, uint256 _amount) public nonReentrant {
        require(block.number >= startBlock, "SolarDistributor: Can not deposit before start");

        PoolInfo storage pool = poolInfo[_pid];
        UserInfo storage user = userInfo[_pid][_msgSender()];

        updatePool(_pid);

        payOrLockupPendingSolar(_pid);

        if (_amount > 0) {
            uint256 beforeDeposit = pool.lpToken.balanceOf(address(this));
            pool.lpToken.safeTransferFrom(_msgSender(), address(this), _amount);
            uint256 afterDeposit = pool.lpToken.balanceOf(address(this));

            _amount = afterDeposit.sub(beforeDeposit);

            if (pool.depositFeeBP > 0) {
                uint256 depositFee = _amount.mul(pool.depositFeeBP).div(10000);
                pool.lpToken.safeTransfer(feeAddress, depositFee);

                _amount = _amount.sub(depositFee);
            }

            user.amount = user.amount.add(_amount);
            pool.totalLp = pool.totalLp.add(_amount);

            if (address(pool.lpToken) == address(solar)) {
                totalSolarInPools = totalSolarInPools.add(_amount);
            }
        }
        user.rewardDebt = user.amount.mul(pool.accSolarPerShare).div(1e12);
        emit Deposit(_msgSender(), _pid, _amount);
    }

    // Withdraw tokens
    function withdraw(uint256 _pid, uint256 _amount) public nonReentrant {
        PoolInfo storage pool = poolInfo[_pid];
        UserInfo storage user = userInfo[_pid][_msgSender()];

        //this will make sure that user can only withdraw from his pool
        require(user.amount >= _amount, "Withdraw: User amount not enough");

        //Cannot withdraw more than pool's balance
        require(pool.totalLp >= _amount, "Withdraw: Pool total not enough");

        updatePool(_pid);

        payOrLockupPendingSolar(_pid);

        if (_amount > 0) {
            user.amount = user.amount.sub(_amount);
            pool.totalLp = pool.totalLp.sub(_amount);
            if (address(pool.lpToken) == address(solar)) {
                totalSolarInPools = totalSolarInPools.sub(_amount);
            }
            pool.lpToken.safeTransfer(_msgSender(), _amount);
        }
        user.rewardDebt = user.amount.mul(pool.accSolarPerShare).div(1e12);
        emit Withdraw(_msgSender(), _pid, _amount);
    }

    // Withdraw without caring about rewards. EMERGENCY ONLY.
    function emergencyWithdraw(uint256 _pid) public nonReentrant {
        PoolInfo storage pool = poolInfo[_pid];
        UserInfo storage user = userInfo[_pid][_msgSender()];
        uint256 amount = user.amount;

        //Cannot withdraw more than pool's balance
        require(pool.totalLp >= amount, "EmergencyWithdraw: Pool total not enough");

        user.amount = 0;
        user.rewardDebt = 0;
        user.rewardLockedUp = 0;
        user.nextHarvestUntil = 0;
        pool.totalLp = pool.totalLp.sub(amount);

        if (address(pool.lpToken) == address(solar)) {
            totalSolarInPools = totalSolarInPools.sub(amount);
        }
        pool.lpToken.safeTransfer(_msgSender(), amount);

        emit EmergencyWithdraw(_msgSender(), _pid, amount);
    }

    // Pay or lockup pending Solar.
    function payOrLockupPendingSolar(uint256 _pid) internal {
        PoolInfo storage pool = poolInfo[_pid];
        UserInfo storage user = userInfo[_pid][_msgSender()];

        if (user.nextHarvestUntil == 0 && block.number >= startBlock) {
            user.nextHarvestUntil = block.timestamp.add(pool.harvestInterval);
        }

        uint256 pending = user.amount.mul(pool.accSolarPerShare).div(1e12).sub(user.rewardDebt);
        if (canHarvest(_pid, _msgSender())) {
            if (pending > 0 || user.rewardLockedUp > 0) {
                uint256 totalRewards = pending.add(user.rewardLockedUp);

                // reset lockup
                totalLockedUpRewards = totalLockedUpRewards.sub(user.rewardLockedUp);
                user.rewardLockedUp = 0;
                user.nextHarvestUntil = block.timestamp.add(pool.harvestInterval);

                // send rewards
                safeSolarTransfer(_msgSender(), totalRewards);
            }
        } else if (pending > 0) {
            user.rewardLockedUp = user.rewardLockedUp.add(pending);
            totalLockedUpRewards = totalLockedUpRewards.add(pending);
            emit RewardLockedUp(_msgSender(), _pid, pending);
        }
    }

    // Safe Solar transfer function, just in case if rounding error causes pool do not have enough Solar.
    function safeSolarTransfer(address _to, uint256 _amount) internal {
        if (solar.balanceOf(address(this)) > totalSolarInPools) {
            //SolarBal = total Solar in SolarDistributor - total Solar in Solar pools, this will make sure that SolarDistributor never transfer rewards from deposited Solar pools
            uint256 SolarBal = solar.balanceOf(address(this)).sub(totalSolarInPools);
            if (_amount >= SolarBal) {
                solar.transfer(_to, SolarBal);
            } else if (_amount > 0) {
                solar.transfer(_to, _amount);
            }
        }
    }

    // Update dev address by the previous dev.
    function setDevAddress(address _devAddress) public {
        require(_msgSender() == devAddress, "setDevAddress: FORBIDDEN");
        require(_devAddress != address(0), "setDevAddress: ZERO");

        emit DevAddressChanged(_msgSender(), devAddress, _devAddress);

        devAddress = _devAddress;
    }

    function setFeeAddress(address _feeAddress) public {
        require(_msgSender() == feeAddress, "setFeeAddress: FORBIDDEN");
        require(_feeAddress != address(0), "setFeeAddress: ZERO");

        emit FeeAddressChanged(_msgSender(), feeAddress, _feeAddress);

        feeAddress = _feeAddress;
    }

    // Pancake has to add hidden dummy pools in order to alter the emission, here we make it simple and transparent to all.
    function updateEmissionRate(uint256 _solarPerBlock) public onlyOperator {
        massUpdatePools();

        emit EmissionRateUpdated(msg.sender, solarPerBlock, _solarPerBlock);
        solarPerBlock = _solarPerBlock;
    }

    function updateAllocPoint(
        uint256 _pid,
        uint256 _allocPoint,
        bool _withUpdate
    ) public onlyOperator {
        if (_withUpdate) {
            massUpdatePools();
        }

        emit AllocPointsUpdated(_msgSender(), poolInfo[_pid].allocPoint, _allocPoint);

        totalAllocPoint = totalAllocPoint.sub(poolInfo[_pid].allocPoint).add(_allocPoint);
        poolInfo[_pid].allocPoint = _allocPoint;
    }

    // Enable support for meta transactions
    function enableMetaTxns() public onlyOperator {
        require(!metaTxnsEnabled, "Meta transactions are already enabled");

        metaTxnsEnabled = true;
        emit MetaTxnsEnabled(_msgSender());
    }

    // Disable support for meta transactions
    function disableMetaTxns() public onlyOperator {
        require(metaTxnsEnabled, "Meta transactions are already disabled");

        metaTxnsEnabled = false;
        emit MetaTxnsDisabled(_msgSender());
    }
}
        

Contract ABI

[{"type":"constructor","stateMutability":"nonpayable","inputs":[{"type":"address","name":"_solar","internalType":"contract ISolarERC20"},{"type":"uint256","name":"_solarPerBlock","internalType":"uint256"}]},{"type":"event","name":"AllocPointsUpdated","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true},{"type":"uint256","name":"previousAmount","internalType":"uint256","indexed":false},{"type":"uint256","name":"newAmount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"Deposit","inputs":[{"type":"address","name":"user","internalType":"address","indexed":true},{"type":"uint256","name":"pid","internalType":"uint256","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"DevAddressChanged","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true},{"type":"address","name":"oldAddress","internalType":"address","indexed":false},{"type":"address","name":"newAddress","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"EmergencyWithdraw","inputs":[{"type":"address","name":"user","internalType":"address","indexed":true},{"type":"uint256","name":"pid","internalType":"uint256","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"EmissionRateUpdated","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true},{"type":"uint256","name":"previousAmount","internalType":"uint256","indexed":false},{"type":"uint256","name":"newAmount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"FeeAddressChanged","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true},{"type":"address","name":"oldAddress","internalType":"address","indexed":false},{"type":"address","name":"newAddress","internalType":"address","indexed":false}],"anonymous":false},{"type":"event","name":"MetaTxnsDisabled","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"MetaTxnsEnabled","inputs":[{"type":"address","name":"caller","internalType":"address","indexed":true}],"anonymous":false},{"type":"event","name":"OperatorTransferred","inputs":[{"type":"address","name":"previousOperator","internalType":"address","indexed":true},{"type":"address","name":"newOperator","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":"RewardLockedUp","inputs":[{"type":"address","name":"user","internalType":"address","indexed":true},{"type":"uint256","name":"pid","internalType":"uint256","indexed":true},{"type":"uint256","name":"amountLockedUp","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"event","name":"Withdraw","inputs":[{"type":"address","name":"user","internalType":"address","indexed":true},{"type":"uint256","name":"pid","internalType":"uint256","indexed":true},{"type":"uint256","name":"amount","internalType":"uint256","indexed":false}],"anonymous":false},{"type":"function","stateMutability":"view","outputs":[{"type":"uint16","name":"","internalType":"uint16"}],"name":"MAXIMUM_DEPOSIT_FEE_RATE","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"MAXIMUM_HARVEST_INTERVAL","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"add","inputs":[{"type":"uint256","name":"_allocPoint","internalType":"uint256"},{"type":"address","name":"_lpToken","internalType":"contract IERC20"},{"type":"uint16","name":"_depositFeeBP","internalType":"uint16"},{"type":"uint256","name":"_harvestInterval","internalType":"uint256"},{"type":"bool","name":"_withUpdate","internalType":"bool"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"canHarvest","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"address","name":"_user","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"deposit","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"uint256","name":"_amount","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"devAddress","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"disableMetaTxns","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"emergencyWithdraw","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"enableMetaTxns","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"feeAddress","inputs":[]},{"type":"function","stateMutability":"pure","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"getMultiplier","inputs":[{"type":"uint256","name":"_from","internalType":"uint256"},{"type":"uint256","name":"_to","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"isTrustedForwarder","inputs":[{"type":"address","name":"forwarder","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"massUpdatePools","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"bool","name":"","internalType":"bool"}],"name":"metaTxnsEnabled","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"address"}],"name":"operator","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":"pendingSolar","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"address","name":"_user","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"lpToken","internalType":"contract IERC20"},{"type":"uint256","name":"allocPoint","internalType":"uint256"},{"type":"uint256","name":"lastRewardBlock","internalType":"uint256"},{"type":"uint256","name":"accSolarPerShare","internalType":"uint256"},{"type":"uint16","name":"depositFeeBP","internalType":"uint16"},{"type":"uint256","name":"harvestInterval","internalType":"uint256"},{"type":"uint256","name":"totalLp","internalType":"uint256"}],"name":"poolInfo","inputs":[{"type":"uint256","name":"","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"poolLength","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"renounceOwnership","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"set","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"uint256","name":"_allocPoint","internalType":"uint256"},{"type":"uint16","name":"_depositFeeBP","internalType":"uint16"},{"type":"uint256","name":"_harvestInterval","internalType":"uint256"},{"type":"bool","name":"_withUpdate","internalType":"bool"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setDevAddress","inputs":[{"type":"address","name":"_devAddress","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"setFeeAddress","inputs":[{"type":"address","name":"_feeAddress","internalType":"address"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"address","name":"","internalType":"contract ISolarERC20"}],"name":"solar","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"solarPerBlock","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"startBlock","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"startFarming","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalAllocPoint","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalLockedUpRewards","inputs":[]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"","internalType":"uint256"}],"name":"totalSolarInPools","inputs":[]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferOperator","inputs":[{"type":"address","name":"newOperator","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"transferOwnership","inputs":[{"type":"address","name":"newOwner","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"updateAllocPoint","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"uint256","name":"_allocPoint","internalType":"uint256"},{"type":"bool","name":"_withUpdate","internalType":"bool"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"updateEmissionRate","inputs":[{"type":"uint256","name":"_solarPerBlock","internalType":"uint256"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"updatePool","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"}]},{"type":"function","stateMutability":"view","outputs":[{"type":"uint256","name":"amount","internalType":"uint256"},{"type":"uint256","name":"rewardDebt","internalType":"uint256"},{"type":"uint256","name":"rewardLockedUp","internalType":"uint256"},{"type":"uint256","name":"nextHarvestUntil","internalType":"uint256"}],"name":"userInfo","inputs":[{"type":"uint256","name":"","internalType":"uint256"},{"type":"address","name":"","internalType":"address"}]},{"type":"function","stateMutability":"nonpayable","outputs":[],"name":"withdraw","inputs":[{"type":"uint256","name":"_pid","internalType":"uint256"},{"type":"uint256","name":"_amount","internalType":"uint256"}]}]
            

Contract Creation Code

0x608060405260006009819055600c55600d805460ff191690553480156200002557600080fd5b5060405162002a6138038062002a618339810160408190526200004891620001b2565b6200005c62000056620000ec565b62000126565b6001805562000070436312cc0300620001ee565b600a55600280546001600160a01b0384166001600160a01b031991821617909155600682905560048054821633908117909155600580548316821790556003805490921681179091556040516000907f74da04524d50c64947f5dd5381ef1a4dca5cba8ed1d816243f9e48aa0b5617ed908290a3505062000215565b6000620000f93362000176565b156200010c575060131936013560601c90565b62000121620001ae60201b62001d9b1760201c565b905090565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b600d5460009060ff168015620001a857506001600160a01b03821673c128b8e142a70e16547484d50b5353478103db99145b92915050565b3390565b60008060408385031215620001c657600080fd5b82516001600160a01b0381168114620001de57600080fd5b6020939093015192949293505050565b600082198211156200021057634e487b7160e01b600052601160045260246000fd5b500190565b61283c80620002256000396000f3fe608060405234801561001057600080fd5b50600436106102275760003560e01c8063578bb42d11610130578063a8c95dc0116100b8578063d761595c1161007c578063d761595c146104ea578063de73149d146104f3578063e2bbb158146104fd578063e6fa6d6d14610510578063f2fde38b1461052357600080fd5b8063a8c95dc01461049c578063af018de8146104a9578063afbcfea1146104bc578063bde4aeca146104c4578063d0d41fe1146104d757600080fd5b8063812c64f1116100ff578063812c64f1146103e95780638705fcd4146104055780638da5cb5b146104185780638dbb1e3a1461042957806393f1a40b1461043c57600080fd5b8063578bb42d146103be578063630b5ba1146103c65780636f22d2c2146103ce578063715018a6146103e157600080fd5b80633cb5ba9e116101b357806348cd4cb11161018257806348cd4cb11461036b57806351eb05a6146103745780635312ea8e14610387578063570ca7351461039a578063572b6c05146103ab57600080fd5b80633cb5ba9e14610333578063412753581461033c578063441a3e701461034f578063474fa6301461036257600080fd5b806317caf6f1116101fa57806317caf6f1146102b65780632143e545146102bf57806329605e77146102d25780632e6c998d146102e55780633ad10ef61461030857600080fd5b8063081e3eda1461022c57806308383640146102435780630ba84cd21461024d5780631526fe2714610260575b600080fd5b6007545b6040519081526020015b60405180910390f35b61024b610536565b005b61024b61025b366004612467565b610613565b61027361026e366004612467565b610688565b604080516001600160a01b039098168852602088019690965294860193909352606085019190915261ffff16608084015260a083015260c082015260e00161023a565b61023060095481565b61024b6102cd3660046124a5565b6106e5565b61024b6102e036600461250e565b6108c6565b6102f86102f336600461252b565b6109bd565b604051901515815260200161023a565b60045461031b906001600160a01b031681565b6040516001600160a01b03909116815260200161023a565b61023060065481565b60055461031b906001600160a01b031681565b61024b61035d36600461255b565b6109fd565b610230600b5481565b610230600a5481565b61024b610382366004612467565b610c29565b61024b610395366004612467565b610de3565b6003546001600160a01b031661031b565b6102f86103b936600461250e565b610f83565b61024b610fba565b61024b611091565b6102306103dc36600461252b565b6110bc565b61024b611249565b6103f26103e881565b60405161ffff909116815260200161023a565b61024b61041336600461250e565b61129e565b6000546001600160a01b031661031b565b61023061043736600461255b565b6113ca565b61047c61044a36600461252b565b600860209081526000928352604080842090915290825290208054600182015460028301546003909301549192909184565b60408051948552602085019390935291830152606082015260800161023a565b600d546102f89060ff1681565b61024b6104b736600461257d565b6113dd565b61024b611691565b61024b6104d23660046125b5565b611781565b61024b6104e536600461250e565b61187e565b610230600c5481565b6102306212750081565b61024b61050b36600461255b565b6119aa565b60025461031b906001600160a01b031681565b61024b61053136600461250e565b611ce1565b6003546001600160a01b031633146105695760405162461bcd60e51b8152600401610560906125ee565b60405180910390fd5b600d5460ff166105ca5760405162461bcd60e51b815260206004820152602660248201527f4d657461207472616e73616374696f6e732061726520616c72656164792064696044820152651cd8589b195960d21b6064820152608401610560565b600d805460ff191690556105dc611d9f565b6001600160a01b03167f096be170ccc67847e55535e7d8334b2afedd95805baedc160005addb9144745060405160405180910390a2565b6003546001600160a01b0316331461063d5760405162461bcd60e51b8152600401610560906125ee565b610645611091565b600654604080519182526020820183905233917feedc6338c9c1ad8f3cd6c90dd09dbe98dbd57e610d3e59a17996d07acb0d9511910160405180910390a2600655565b6007818154811061069857600080fd5b600091825260209091206007909102018054600182015460028301546003840154600485015460058601546006909601546001600160a01b03909516965092949193909261ffff16919087565b6106ed611d9f565b6001600160a01b03166107086000546001600160a01b031690565b6001600160a01b03161461072e5760405162461bcd60e51b815260040161056090612632565b6103e861ffff841611156107845760405162461bcd60e51b815260206004820152601960248201527f7365743a206465706f7369742066656520746f6f2068696768000000000000006044820152606401610560565b621275008211156107d75760405162461bcd60e51b815260206004820152601d60248201527f7365743a20696e76616c6964206861727665737420696e74657276616c0000006044820152606401610560565b80156107e5576107e5611091565b61082884610822600788815481106107ff576107ff612667565b906000526020600020906007020160010154600954611dc190919063ffffffff16565b90611dcd565b600981905550836007868154811061084257610842612667565b906000526020600020906007020160010181905550826007868154811061086b5761086b612667565b906000526020600020906007020160040160006101000a81548161ffff021916908361ffff16021790555081600786815481106108aa576108aa612667565b9060005260206000209060070201600501819055505050505050565b6003546001600160a01b031633146108f05760405162461bcd60e51b8152600401610560906125ee565b6001600160a01b0381166109615760405162461bcd60e51b815260206004820152603260248201527f5472616e736665724f70657261746f723a206e6577206f70657261746f7220696044820152717320746865207a65726f206164647265737360701b6064820152608401610560565b6003546040516001600160a01b038084169216907f74da04524d50c64947f5dd5381ef1a4dca5cba8ed1d816243f9e48aa0b5617ed90600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b60008281526008602090815260408083206001600160a01b03851684529091528120600a5443108015906109f5575080600301544210155b949350505050565b60026001541415610a205760405162461bcd60e51b81526004016105609061267d565b6002600181905550600060078381548110610a3d57610a3d612667565b60009182526020808320868452600890915260408320600790920201925081610a64611d9f565b6001600160a01b03166001600160a01b0316815260200190815260200160002090508281600001541015610ada5760405162461bcd60e51b815260206004820181905260248201527f57697468647261773a205573657220616d6f756e74206e6f7420656e6f7567686044820152606401610560565b8282600601541015610b2e5760405162461bcd60e51b815260206004820152601f60248201527f57697468647261773a20506f6f6c20746f74616c206e6f7420656e6f756768006044820152606401610560565b610b3784610c29565b610b4084611dd9565b8215610bae578054610b529084611dc1565b81556006820154610b639084611dc1565b600683015560025482546001600160a01b0390811691161415610b9157600c54610b8d9084611dc1565b600c555b610bae610b9c611d9f565b83546001600160a01b03169085611fa8565b60038201548154610bcf9164e8d4a5100091610bc991612010565b9061201c565b600182015583610bdd611d9f565b6001600160a01b03167ff279e6a1f5e320cca91135676d9cb6e44ca8a08c0b88342bcdb1144f6511b56885604051610c1791815260200190565b60405180910390a35050600180555050565b600060078281548110610c3e57610c3e612667565b9060005260206000209060070201905080600201544311610c5d575050565b6006810154801580610c7157506001820154155b15610c8157504360029091015550565b6000610c918360020154436113ca565b90506000610cbe600954610bc98660010154610cb86006548761201090919063ffffffff16565b90612010565b6002546004549192506001600160a01b03908116916340c10f199116610ce584600a61201c565b6040516001600160e01b031960e085901b1681526001600160a01b0390921660048301526024820152604401600060405180830381600087803b158015610d2b57600080fd5b505af1158015610d3f573d6000803e3d6000fd5b50506002546040516340c10f1960e01b8152306004820152602481018590526001600160a01b0390911692506340c10f199150604401600060405180830381600087803b158015610d8f57600080fd5b505af1158015610da3573d6000803e3d6000fd5b5050506006850154610dce9150610dc390610bc98464e8d4a51000612010565b600386015490611dcd565b60038501555050436002909201919091555050565b60026001541415610e065760405162461bcd60e51b81526004016105609061267d565b6002600181905550600060078281548110610e2357610e23612667565b60009182526020808320858452600890915260408320600790920201925081610e4a611d9f565b6001600160a01b0316815260208101919091526040016000208054600684015491925090811115610ece5760405162461bcd60e51b815260206004820152602860248201527f456d657267656e637957697468647261773a20506f6f6c20746f74616c206e6f6044820152670e840cadcdeeaced60c31b6064820152608401610560565b6000808355600183018190556002830181905560038301556006830154610ef59082611dc1565b600684015560025483546001600160a01b0390811691161415610f2357600c54610f1f9082611dc1565b600c555b610f40610f2e611d9f565b84546001600160a01b03169083611fa8565b83610f49611d9f565b6001600160a01b03167fbb757047c2b5f3974fe26b7c10f732e7bce710b0952a71082702781e62ae059583604051610c1791815260200190565b600d5460009060ff168015610fb457506001600160a01b03821673c128b8e142a70e16547484d50b5353478103db99145b92915050565b6003546001600160a01b03163314610fe45760405162461bcd60e51b8152600401610560906125ee565b600d5460ff16156110455760405162461bcd60e51b815260206004820152602560248201527f4d657461207472616e73616374696f6e732061726520616c726561647920656e60448201526418589b195960da1b6064820152608401610560565b600d805460ff1916600117905561105a611d9f565b6001600160a01b03167f92e4c08d47b71e8dc051232b8e475ec296489a67a4ba5cca88ff20fb6ac499e660405160405180910390a2565b60075460005b818110156110b8576110a881610c29565b6110b1816126ca565b9050611097565b5050565b600080600784815481106110d2576110d2612667565b600091825260208083208784526008825260408085206001600160a01b03898116875293528085206007949094029091016003810154815492516370a0823160e01b815230600482015291965093949291909116906370a082319060240160206040518083038186803b15801561114857600080fd5b505afa15801561115c573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061118091906126e5565b905083600201544311801561119457508015155b156111f45760006111a98560020154436113ca565b905060006111d0600954610bc98860010154610cb86006548761201090919063ffffffff16565b90506111ef6111e884610bc98464e8d4a51000612010565b8590611dcd565b935050505b6000611224846001015461121e64e8d4a51000610bc987896000015461201090919063ffffffff16565b90611dc1565b905061123d846002015482611dcd90919063ffffffff16565b98975050505050505050565b611251611d9f565b6001600160a01b031661126c6000546001600160a01b031690565b6001600160a01b0316146112925760405162461bcd60e51b815260040161056090612632565b61129c6000612028565b565b6005546001600160a01b03166112b2611d9f565b6001600160a01b0316146113085760405162461bcd60e51b815260206004820152601860248201527f736574466565416464726573733a20464f5242494444454e00000000000000006044820152606401610560565b6001600160a01b0381166113545760405162461bcd60e51b8152602060048201526013602482015272736574466565416464726573733a205a45524f60681b6044820152606401610560565b61135c611d9f565b600554604080516001600160a01b039283168152848316602082015292909116917f6690a53895b5691c039238b384bd857e65c42adcc727775381e02cb90a122613910160405180910390a2600580546001600160a01b0319166001600160a01b0392909216919091179055565b60006113d68284611dc1565b9392505050565b6113e5611d9f565b6001600160a01b03166114006000546001600160a01b031690565b6001600160a01b0316146114265760405162461bcd60e51b815260040161056090612632565b6103e861ffff8416111561147c5760405162461bcd60e51b815260206004820152601960248201527f6164643a206465706f7369742066656520746f6f2068696768000000000000006044820152606401610560565b621275008211156114cf5760405162461bcd60e51b815260206004820152601d60248201527f6164643a20696e76616c6964206861727665737420696e74657276616c0000006044820152606401610560565b80156114dd576114dd611091565b6000600a5443116114f057600a546114f2565b435b6009549091506115029087611dcd565b6009556040805160e0810182526001600160a01b0396871681526020810197885290810191825260006060820181815261ffff9687166080840190815260a0840196875260c08401838152600780546001810182559481905294517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c6889490950293840180546001600160a01b03191695909a169490941790985597517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68982015591517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68a83015595517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68b82015593517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68c8501805461ffff19169190941617909255517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68d8301555090517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68e90910155565b611699611d9f565b6001600160a01b03166116b46000546001600160a01b031690565b6001600160a01b0316146116da5760405162461bcd60e51b815260040161056090612632565b600a54431061172b5760405162461bcd60e51b815260206004820152601b60248201527f4572726f723a3a4661726d207374617274656420616c726561647900000000006044820152606401610560565b60075460005b818110156117795760006007828154811061174e5761174e612667565b906000526020600020906007020190504381600201819055505080611772906126ca565b9050611731565b505043600a55565b6003546001600160a01b031633146117ab5760405162461bcd60e51b8152600401610560906125ee565b80156117b9576117b9611091565b6117c1611d9f565b6001600160a01b03167f802633c8d26237616d81bdac01bc40fcdf36e098832601582ec19d7e431c5ef3600785815481106117fe576117fe612667565b90600052602060002090600702016001015484604051611828929190918252602082015260400190565b60405180910390a261184a82610822600786815481106107ff576107ff612667565b600981905550816007848154811061186457611864612667565b906000526020600020906007020160010181905550505050565b6004546001600160a01b0316611892611d9f565b6001600160a01b0316146118e85760405162461bcd60e51b815260206004820152601860248201527f736574446576416464726573733a20464f5242494444454e00000000000000006044820152606401610560565b6001600160a01b0381166119345760405162461bcd60e51b8152602060048201526013602482015272736574446576416464726573733a205a45524f60681b6044820152606401610560565b61193c611d9f565b600454604080516001600160a01b039283168152848316602082015292909116917fd36d63f6c513a911d7912853de740af476b0fbb569aa769e1a4f5bfa37a325c4910160405180910390a2600480546001600160a01b0319166001600160a01b0392909216919091179055565b600260015414156119cd5760405162461bcd60e51b81526004016105609061267d565b6002600155600a54431015611a3b5760405162461bcd60e51b815260206004820152602e60248201527f536f6c61724469737472696275746f723a2043616e206e6f74206465706f736960448201526d1d081899599bdc99481cdd185c9d60921b6064820152608401610560565b600060078381548110611a5057611a50612667565b60009182526020808320868452600890915260408320600790920201925081611a77611d9f565b6001600160a01b03166001600160a01b031681526020019081526020016000209050611aa284610c29565b611aab84611dd9565b8215611c7e5781546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a082319060240160206040518083038186803b158015611af457600080fd5b505afa158015611b08573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b2c91906126e5565b9050611b4c611b39611d9f565b84546001600160a01b0316903087612078565b82546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a082319060240160206040518083038186803b158015611b8f57600080fd5b505afa158015611ba3573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611bc791906126e5565b9050611bd38183611dc1565b600485015490955061ffff1615611c30576004840154600090611c039061271090610bc990899061ffff16612010565b6005548654919250611c22916001600160a01b03908116911683611fa8565b611c2c8682611dc1565b9550505b8254611c3c9086611dcd565b83556006840154611c4d9086611dcd565b600685015560025484546001600160a01b0390811691161415611c7b57600c54611c779086611dcd565b600c555b50505b60038201548154611c999164e8d4a5100091610bc991612010565b600182015583611ca7611d9f565b6001600160a01b03167f90890809c654f11d6e72a28fa60149770a0d11ec6c92319d6ceb2bb0a4ea1a1585604051610c1791815260200190565b611ce9611d9f565b6001600160a01b0316611d046000546001600160a01b031690565b6001600160a01b031614611d2a5760405162461bcd60e51b815260040161056090612632565b6001600160a01b038116611d8f5760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610560565b611d9881612028565b50565b3390565b6000611daa33610f83565b15611dbc575060131936013560601c90565b503390565b60006113d682846126fe565b60006113d68284612715565b600060078281548110611dee57611dee612667565b60009182526020808320858452600890915260408320600790920201925081611e15611d9f565b6001600160a01b03166001600160a01b03168152602001908152602001600020905080600301546000148015611e4d5750600a544310155b15611e68576005820154611e62904290611dcd565b60038201555b6000611e96826001015461121e64e8d4a51000610bc98760030154876000015461201090919063ffffffff16565b9050611ea4846102f3611d9f565b15611f2c576000811180611ebc575060008260020154115b15611f27576000611eda836002015483611dcd90919063ffffffff16565b9050611ef58360020154600b54611dc190919063ffffffff16565b600b55600060028401556005840154611f0f904290611dcd565b6003840155611f25611f1f611d9f565b826120b0565b505b611fa2565b8015611fa2576002820154611f419082611dcd565b6002830155600b54611f539082611dcd565b600b5583611f5f611d9f565b6001600160a01b03167fee470483107f579a55c754fa00613c45a9a3b617a418b39cb0be97e5381ba7c183604051611f9991815260200190565b60405180910390a35b50505050565b6040516001600160a01b03831660248201526044810182905261200b90849063a9059cbb60e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915261228a565b505050565b60006113d6828461272d565b60006113d6828461274c565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6040516001600160a01b0380851660248301528316604482015260648101829052611fa29085906323b872dd60e01b90608401611fd4565b600c546002546040516370a0823160e01b81523060048201526001600160a01b03909116906370a082319060240160206040518083038186803b1580156120f657600080fd5b505afa15801561210a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061212e91906126e5565b11156110b857600c546002546040516370a0823160e01b81523060048201526000926121bb9290916001600160a01b03909116906370a082319060240160206040518083038186803b15801561218357600080fd5b505afa158015612197573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061121e91906126e5565b905080821061224b5760025460405163a9059cbb60e01b81526001600160a01b038581166004830152602482018490529091169063a9059cbb906044015b602060405180830381600087803b15801561221357600080fd5b505af1158015612227573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611fa2919061276e565b811561200b5760025460405163a9059cbb60e01b81526001600160a01b038581166004830152602482018590529091169063a9059cbb906044016121f9565b60006122df826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b031661235c9092919063ffffffff16565b80519091501561200b57808060200190518101906122fd919061276e565b61200b5760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610560565b60606109f5848460008585843b6123b55760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610560565b600080866001600160a01b031685876040516123d191906127b7565b60006040518083038185875af1925050503d806000811461240e576040519150601f19603f3d011682016040523d82523d6000602084013e612413565b606091505b509150915061242382828661242e565b979650505050505050565b6060831561243d5750816113d6565b82511561244d5782518084602001fd5b8160405162461bcd60e51b815260040161056091906127d3565b60006020828403121561247957600080fd5b5035919050565b803561ffff8116811461249257600080fd5b919050565b8015158114611d9857600080fd5b600080600080600060a086880312156124bd57600080fd5b85359450602086013593506124d460408701612480565b92506060860135915060808601356124eb81612497565b809150509295509295909350565b6001600160a01b0381168114611d9857600080fd5b60006020828403121561252057600080fd5b81356113d6816124f9565b6000806040838503121561253e57600080fd5b823591506020830135612550816124f9565b809150509250929050565b6000806040838503121561256e57600080fd5b50508035926020909101359150565b600080600080600060a0868803121561259557600080fd5b8535945060208601356125a7816124f9565b93506124d460408701612480565b6000806000606084860312156125ca57600080fd5b833592506020840135915060408401356125e381612497565b809150509250925092565b60208082526024908201527f4f70657261746f723a2063616c6c6572206973206e6f7420746865206f70657260408201526330ba37b960e11b606082015260800190565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b634e487b7160e01b600052603260045260246000fd5b6020808252601f908201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604082015260600190565b634e487b7160e01b600052601160045260246000fd5b60006000198214156126de576126de6126b4565b5060010190565b6000602082840312156126f757600080fd5b5051919050565b600082821015612710576127106126b4565b500390565b60008219821115612728576127286126b4565b500190565b6000816000190483118215151615612747576127476126b4565b500290565b60008261276957634e487b7160e01b600052601260045260246000fd5b500490565b60006020828403121561278057600080fd5b81516113d681612497565b60005b838110156127a657818101518382015260200161278e565b83811115611fa25750506000910152565b600082516127c981846020870161278b565b9190910192915050565b60208152600082518060208401526127f281604085016020870161278b565b601f01601f1916919091016040019291505056fea2646970667358221220a35317482bdd824ae392fc837a8ebd80d30ad0350c2cc2d209910c66db3bc77964736f6c634300080900330000000000000000000000005d1af739fd538d363fd61a59d3cbb7b70784a3ac000000000000000000000000000000000000000000000000000000000000001e

Deployed ByteCode

0x608060405234801561001057600080fd5b50600436106102275760003560e01c8063578bb42d11610130578063a8c95dc0116100b8578063d761595c1161007c578063d761595c146104ea578063de73149d146104f3578063e2bbb158146104fd578063e6fa6d6d14610510578063f2fde38b1461052357600080fd5b8063a8c95dc01461049c578063af018de8146104a9578063afbcfea1146104bc578063bde4aeca146104c4578063d0d41fe1146104d757600080fd5b8063812c64f1116100ff578063812c64f1146103e95780638705fcd4146104055780638da5cb5b146104185780638dbb1e3a1461042957806393f1a40b1461043c57600080fd5b8063578bb42d146103be578063630b5ba1146103c65780636f22d2c2146103ce578063715018a6146103e157600080fd5b80633cb5ba9e116101b357806348cd4cb11161018257806348cd4cb11461036b57806351eb05a6146103745780635312ea8e14610387578063570ca7351461039a578063572b6c05146103ab57600080fd5b80633cb5ba9e14610333578063412753581461033c578063441a3e701461034f578063474fa6301461036257600080fd5b806317caf6f1116101fa57806317caf6f1146102b65780632143e545146102bf57806329605e77146102d25780632e6c998d146102e55780633ad10ef61461030857600080fd5b8063081e3eda1461022c57806308383640146102435780630ba84cd21461024d5780631526fe2714610260575b600080fd5b6007545b6040519081526020015b60405180910390f35b61024b610536565b005b61024b61025b366004612467565b610613565b61027361026e366004612467565b610688565b604080516001600160a01b039098168852602088019690965294860193909352606085019190915261ffff16608084015260a083015260c082015260e00161023a565b61023060095481565b61024b6102cd3660046124a5565b6106e5565b61024b6102e036600461250e565b6108c6565b6102f86102f336600461252b565b6109bd565b604051901515815260200161023a565b60045461031b906001600160a01b031681565b6040516001600160a01b03909116815260200161023a565b61023060065481565b60055461031b906001600160a01b031681565b61024b61035d36600461255b565b6109fd565b610230600b5481565b610230600a5481565b61024b610382366004612467565b610c29565b61024b610395366004612467565b610de3565b6003546001600160a01b031661031b565b6102f86103b936600461250e565b610f83565b61024b610fba565b61024b611091565b6102306103dc36600461252b565b6110bc565b61024b611249565b6103f26103e881565b60405161ffff909116815260200161023a565b61024b61041336600461250e565b61129e565b6000546001600160a01b031661031b565b61023061043736600461255b565b6113ca565b61047c61044a36600461252b565b600860209081526000928352604080842090915290825290208054600182015460028301546003909301549192909184565b60408051948552602085019390935291830152606082015260800161023a565b600d546102f89060ff1681565b61024b6104b736600461257d565b6113dd565b61024b611691565b61024b6104d23660046125b5565b611781565b61024b6104e536600461250e565b61187e565b610230600c5481565b6102306212750081565b61024b61050b36600461255b565b6119aa565b60025461031b906001600160a01b031681565b61024b61053136600461250e565b611ce1565b6003546001600160a01b031633146105695760405162461bcd60e51b8152600401610560906125ee565b60405180910390fd5b600d5460ff166105ca5760405162461bcd60e51b815260206004820152602660248201527f4d657461207472616e73616374696f6e732061726520616c72656164792064696044820152651cd8589b195960d21b6064820152608401610560565b600d805460ff191690556105dc611d9f565b6001600160a01b03167f096be170ccc67847e55535e7d8334b2afedd95805baedc160005addb9144745060405160405180910390a2565b6003546001600160a01b0316331461063d5760405162461bcd60e51b8152600401610560906125ee565b610645611091565b600654604080519182526020820183905233917feedc6338c9c1ad8f3cd6c90dd09dbe98dbd57e610d3e59a17996d07acb0d9511910160405180910390a2600655565b6007818154811061069857600080fd5b600091825260209091206007909102018054600182015460028301546003840154600485015460058601546006909601546001600160a01b03909516965092949193909261ffff16919087565b6106ed611d9f565b6001600160a01b03166107086000546001600160a01b031690565b6001600160a01b03161461072e5760405162461bcd60e51b815260040161056090612632565b6103e861ffff841611156107845760405162461bcd60e51b815260206004820152601960248201527f7365743a206465706f7369742066656520746f6f2068696768000000000000006044820152606401610560565b621275008211156107d75760405162461bcd60e51b815260206004820152601d60248201527f7365743a20696e76616c6964206861727665737420696e74657276616c0000006044820152606401610560565b80156107e5576107e5611091565b61082884610822600788815481106107ff576107ff612667565b906000526020600020906007020160010154600954611dc190919063ffffffff16565b90611dcd565b600981905550836007868154811061084257610842612667565b906000526020600020906007020160010181905550826007868154811061086b5761086b612667565b906000526020600020906007020160040160006101000a81548161ffff021916908361ffff16021790555081600786815481106108aa576108aa612667565b9060005260206000209060070201600501819055505050505050565b6003546001600160a01b031633146108f05760405162461bcd60e51b8152600401610560906125ee565b6001600160a01b0381166109615760405162461bcd60e51b815260206004820152603260248201527f5472616e736665724f70657261746f723a206e6577206f70657261746f7220696044820152717320746865207a65726f206164647265737360701b6064820152608401610560565b6003546040516001600160a01b038084169216907f74da04524d50c64947f5dd5381ef1a4dca5cba8ed1d816243f9e48aa0b5617ed90600090a3600380546001600160a01b0319166001600160a01b0392909216919091179055565b60008281526008602090815260408083206001600160a01b03851684529091528120600a5443108015906109f5575080600301544210155b949350505050565b60026001541415610a205760405162461bcd60e51b81526004016105609061267d565b6002600181905550600060078381548110610a3d57610a3d612667565b60009182526020808320868452600890915260408320600790920201925081610a64611d9f565b6001600160a01b03166001600160a01b0316815260200190815260200160002090508281600001541015610ada5760405162461bcd60e51b815260206004820181905260248201527f57697468647261773a205573657220616d6f756e74206e6f7420656e6f7567686044820152606401610560565b8282600601541015610b2e5760405162461bcd60e51b815260206004820152601f60248201527f57697468647261773a20506f6f6c20746f74616c206e6f7420656e6f756768006044820152606401610560565b610b3784610c29565b610b4084611dd9565b8215610bae578054610b529084611dc1565b81556006820154610b639084611dc1565b600683015560025482546001600160a01b0390811691161415610b9157600c54610b8d9084611dc1565b600c555b610bae610b9c611d9f565b83546001600160a01b03169085611fa8565b60038201548154610bcf9164e8d4a5100091610bc991612010565b9061201c565b600182015583610bdd611d9f565b6001600160a01b03167ff279e6a1f5e320cca91135676d9cb6e44ca8a08c0b88342bcdb1144f6511b56885604051610c1791815260200190565b60405180910390a35050600180555050565b600060078281548110610c3e57610c3e612667565b9060005260206000209060070201905080600201544311610c5d575050565b6006810154801580610c7157506001820154155b15610c8157504360029091015550565b6000610c918360020154436113ca565b90506000610cbe600954610bc98660010154610cb86006548761201090919063ffffffff16565b90612010565b6002546004549192506001600160a01b03908116916340c10f199116610ce584600a61201c565b6040516001600160e01b031960e085901b1681526001600160a01b0390921660048301526024820152604401600060405180830381600087803b158015610d2b57600080fd5b505af1158015610d3f573d6000803e3d6000fd5b50506002546040516340c10f1960e01b8152306004820152602481018590526001600160a01b0390911692506340c10f199150604401600060405180830381600087803b158015610d8f57600080fd5b505af1158015610da3573d6000803e3d6000fd5b5050506006850154610dce9150610dc390610bc98464e8d4a51000612010565b600386015490611dcd565b60038501555050436002909201919091555050565b60026001541415610e065760405162461bcd60e51b81526004016105609061267d565b6002600181905550600060078281548110610e2357610e23612667565b60009182526020808320858452600890915260408320600790920201925081610e4a611d9f565b6001600160a01b0316815260208101919091526040016000208054600684015491925090811115610ece5760405162461bcd60e51b815260206004820152602860248201527f456d657267656e637957697468647261773a20506f6f6c20746f74616c206e6f6044820152670e840cadcdeeaced60c31b6064820152608401610560565b6000808355600183018190556002830181905560038301556006830154610ef59082611dc1565b600684015560025483546001600160a01b0390811691161415610f2357600c54610f1f9082611dc1565b600c555b610f40610f2e611d9f565b84546001600160a01b03169083611fa8565b83610f49611d9f565b6001600160a01b03167fbb757047c2b5f3974fe26b7c10f732e7bce710b0952a71082702781e62ae059583604051610c1791815260200190565b600d5460009060ff168015610fb457506001600160a01b03821673c128b8e142a70e16547484d50b5353478103db99145b92915050565b6003546001600160a01b03163314610fe45760405162461bcd60e51b8152600401610560906125ee565b600d5460ff16156110455760405162461bcd60e51b815260206004820152602560248201527f4d657461207472616e73616374696f6e732061726520616c726561647920656e60448201526418589b195960da1b6064820152608401610560565b600d805460ff1916600117905561105a611d9f565b6001600160a01b03167f92e4c08d47b71e8dc051232b8e475ec296489a67a4ba5cca88ff20fb6ac499e660405160405180910390a2565b60075460005b818110156110b8576110a881610c29565b6110b1816126ca565b9050611097565b5050565b600080600784815481106110d2576110d2612667565b600091825260208083208784526008825260408085206001600160a01b03898116875293528085206007949094029091016003810154815492516370a0823160e01b815230600482015291965093949291909116906370a082319060240160206040518083038186803b15801561114857600080fd5b505afa15801561115c573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061118091906126e5565b905083600201544311801561119457508015155b156111f45760006111a98560020154436113ca565b905060006111d0600954610bc98860010154610cb86006548761201090919063ffffffff16565b90506111ef6111e884610bc98464e8d4a51000612010565b8590611dcd565b935050505b6000611224846001015461121e64e8d4a51000610bc987896000015461201090919063ffffffff16565b90611dc1565b905061123d846002015482611dcd90919063ffffffff16565b98975050505050505050565b611251611d9f565b6001600160a01b031661126c6000546001600160a01b031690565b6001600160a01b0316146112925760405162461bcd60e51b815260040161056090612632565b61129c6000612028565b565b6005546001600160a01b03166112b2611d9f565b6001600160a01b0316146113085760405162461bcd60e51b815260206004820152601860248201527f736574466565416464726573733a20464f5242494444454e00000000000000006044820152606401610560565b6001600160a01b0381166113545760405162461bcd60e51b8152602060048201526013602482015272736574466565416464726573733a205a45524f60681b6044820152606401610560565b61135c611d9f565b600554604080516001600160a01b039283168152848316602082015292909116917f6690a53895b5691c039238b384bd857e65c42adcc727775381e02cb90a122613910160405180910390a2600580546001600160a01b0319166001600160a01b0392909216919091179055565b60006113d68284611dc1565b9392505050565b6113e5611d9f565b6001600160a01b03166114006000546001600160a01b031690565b6001600160a01b0316146114265760405162461bcd60e51b815260040161056090612632565b6103e861ffff8416111561147c5760405162461bcd60e51b815260206004820152601960248201527f6164643a206465706f7369742066656520746f6f2068696768000000000000006044820152606401610560565b621275008211156114cf5760405162461bcd60e51b815260206004820152601d60248201527f6164643a20696e76616c6964206861727665737420696e74657276616c0000006044820152606401610560565b80156114dd576114dd611091565b6000600a5443116114f057600a546114f2565b435b6009549091506115029087611dcd565b6009556040805160e0810182526001600160a01b0396871681526020810197885290810191825260006060820181815261ffff9687166080840190815260a0840196875260c08401838152600780546001810182559481905294517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c6889490950293840180546001600160a01b03191695909a169490941790985597517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68982015591517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68a83015595517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68b82015593517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68c8501805461ffff19169190941617909255517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68d8301555090517fa66cc928b5edb82af9bd49922954155ab7b0942694bea4ce44661d9a8736c68e90910155565b611699611d9f565b6001600160a01b03166116b46000546001600160a01b031690565b6001600160a01b0316146116da5760405162461bcd60e51b815260040161056090612632565b600a54431061172b5760405162461bcd60e51b815260206004820152601b60248201527f4572726f723a3a4661726d207374617274656420616c726561647900000000006044820152606401610560565b60075460005b818110156117795760006007828154811061174e5761174e612667565b906000526020600020906007020190504381600201819055505080611772906126ca565b9050611731565b505043600a55565b6003546001600160a01b031633146117ab5760405162461bcd60e51b8152600401610560906125ee565b80156117b9576117b9611091565b6117c1611d9f565b6001600160a01b03167f802633c8d26237616d81bdac01bc40fcdf36e098832601582ec19d7e431c5ef3600785815481106117fe576117fe612667565b90600052602060002090600702016001015484604051611828929190918252602082015260400190565b60405180910390a261184a82610822600786815481106107ff576107ff612667565b600981905550816007848154811061186457611864612667565b906000526020600020906007020160010181905550505050565b6004546001600160a01b0316611892611d9f565b6001600160a01b0316146118e85760405162461bcd60e51b815260206004820152601860248201527f736574446576416464726573733a20464f5242494444454e00000000000000006044820152606401610560565b6001600160a01b0381166119345760405162461bcd60e51b8152602060048201526013602482015272736574446576416464726573733a205a45524f60681b6044820152606401610560565b61193c611d9f565b600454604080516001600160a01b039283168152848316602082015292909116917fd36d63f6c513a911d7912853de740af476b0fbb569aa769e1a4f5bfa37a325c4910160405180910390a2600480546001600160a01b0319166001600160a01b0392909216919091179055565b600260015414156119cd5760405162461bcd60e51b81526004016105609061267d565b6002600155600a54431015611a3b5760405162461bcd60e51b815260206004820152602e60248201527f536f6c61724469737472696275746f723a2043616e206e6f74206465706f736960448201526d1d081899599bdc99481cdd185c9d60921b6064820152608401610560565b600060078381548110611a5057611a50612667565b60009182526020808320868452600890915260408320600790920201925081611a77611d9f565b6001600160a01b03166001600160a01b031681526020019081526020016000209050611aa284610c29565b611aab84611dd9565b8215611c7e5781546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a082319060240160206040518083038186803b158015611af457600080fd5b505afa158015611b08573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b2c91906126e5565b9050611b4c611b39611d9f565b84546001600160a01b0316903087612078565b82546040516370a0823160e01b81523060048201526000916001600160a01b0316906370a082319060240160206040518083038186803b158015611b8f57600080fd5b505afa158015611ba3573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611bc791906126e5565b9050611bd38183611dc1565b600485015490955061ffff1615611c30576004840154600090611c039061271090610bc990899061ffff16612010565b6005548654919250611c22916001600160a01b03908116911683611fa8565b611c2c8682611dc1565b9550505b8254611c3c9086611dcd565b83556006840154611c4d9086611dcd565b600685015560025484546001600160a01b0390811691161415611c7b57600c54611c779086611dcd565b600c555b50505b60038201548154611c999164e8d4a5100091610bc991612010565b600182015583611ca7611d9f565b6001600160a01b03167f90890809c654f11d6e72a28fa60149770a0d11ec6c92319d6ceb2bb0a4ea1a1585604051610c1791815260200190565b611ce9611d9f565b6001600160a01b0316611d046000546001600160a01b031690565b6001600160a01b031614611d2a5760405162461bcd60e51b815260040161056090612632565b6001600160a01b038116611d8f5760405162461bcd60e51b815260206004820152602660248201527f4f776e61626c653a206e6577206f776e657220697320746865207a65726f206160448201526564647265737360d01b6064820152608401610560565b611d9881612028565b50565b3390565b6000611daa33610f83565b15611dbc575060131936013560601c90565b503390565b60006113d682846126fe565b60006113d68284612715565b600060078281548110611dee57611dee612667565b60009182526020808320858452600890915260408320600790920201925081611e15611d9f565b6001600160a01b03166001600160a01b03168152602001908152602001600020905080600301546000148015611e4d5750600a544310155b15611e68576005820154611e62904290611dcd565b60038201555b6000611e96826001015461121e64e8d4a51000610bc98760030154876000015461201090919063ffffffff16565b9050611ea4846102f3611d9f565b15611f2c576000811180611ebc575060008260020154115b15611f27576000611eda836002015483611dcd90919063ffffffff16565b9050611ef58360020154600b54611dc190919063ffffffff16565b600b55600060028401556005840154611f0f904290611dcd565b6003840155611f25611f1f611d9f565b826120b0565b505b611fa2565b8015611fa2576002820154611f419082611dcd565b6002830155600b54611f539082611dcd565b600b5583611f5f611d9f565b6001600160a01b03167fee470483107f579a55c754fa00613c45a9a3b617a418b39cb0be97e5381ba7c183604051611f9991815260200190565b60405180910390a35b50505050565b6040516001600160a01b03831660248201526044810182905261200b90849063a9059cbb60e01b906064015b60408051601f198184030181529190526020810180516001600160e01b03166001600160e01b03199093169290921790915261228a565b505050565b60006113d6828461272d565b60006113d6828461274c565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b6040516001600160a01b0380851660248301528316604482015260648101829052611fa29085906323b872dd60e01b90608401611fd4565b600c546002546040516370a0823160e01b81523060048201526001600160a01b03909116906370a082319060240160206040518083038186803b1580156120f657600080fd5b505afa15801561210a573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061212e91906126e5565b11156110b857600c546002546040516370a0823160e01b81523060048201526000926121bb9290916001600160a01b03909116906370a082319060240160206040518083038186803b15801561218357600080fd5b505afa158015612197573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061121e91906126e5565b905080821061224b5760025460405163a9059cbb60e01b81526001600160a01b038581166004830152602482018490529091169063a9059cbb906044015b602060405180830381600087803b15801561221357600080fd5b505af1158015612227573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611fa2919061276e565b811561200b5760025460405163a9059cbb60e01b81526001600160a01b038581166004830152602482018590529091169063a9059cbb906044016121f9565b60006122df826040518060400160405280602081526020017f5361666545524332303a206c6f772d6c6576656c2063616c6c206661696c6564815250856001600160a01b031661235c9092919063ffffffff16565b80519091501561200b57808060200190518101906122fd919061276e565b61200b5760405162461bcd60e51b815260206004820152602a60248201527f5361666545524332303a204552433230206f7065726174696f6e20646964206e6044820152691bdd081cdd58d8d9595960b21b6064820152608401610560565b60606109f5848460008585843b6123b55760405162461bcd60e51b815260206004820152601d60248201527f416464726573733a2063616c6c20746f206e6f6e2d636f6e74726163740000006044820152606401610560565b600080866001600160a01b031685876040516123d191906127b7565b60006040518083038185875af1925050503d806000811461240e576040519150601f19603f3d011682016040523d82523d6000602084013e612413565b606091505b509150915061242382828661242e565b979650505050505050565b6060831561243d5750816113d6565b82511561244d5782518084602001fd5b8160405162461bcd60e51b815260040161056091906127d3565b60006020828403121561247957600080fd5b5035919050565b803561ffff8116811461249257600080fd5b919050565b8015158114611d9857600080fd5b600080600080600060a086880312156124bd57600080fd5b85359450602086013593506124d460408701612480565b92506060860135915060808601356124eb81612497565b809150509295509295909350565b6001600160a01b0381168114611d9857600080fd5b60006020828403121561252057600080fd5b81356113d6816124f9565b6000806040838503121561253e57600080fd5b823591506020830135612550816124f9565b809150509250929050565b6000806040838503121561256e57600080fd5b50508035926020909101359150565b600080600080600060a0868803121561259557600080fd5b8535945060208601356125a7816124f9565b93506124d460408701612480565b6000806000606084860312156125ca57600080fd5b833592506020840135915060408401356125e381612497565b809150509250925092565b60208082526024908201527f4f70657261746f723a2063616c6c6572206973206e6f7420746865206f70657260408201526330ba37b960e11b606082015260800190565b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b634e487b7160e01b600052603260045260246000fd5b6020808252601f908201527f5265656e7472616e637947756172643a207265656e7472616e742063616c6c00604082015260600190565b634e487b7160e01b600052601160045260246000fd5b60006000198214156126de576126de6126b4565b5060010190565b6000602082840312156126f757600080fd5b5051919050565b600082821015612710576127106126b4565b500390565b60008219821115612728576127286126b4565b500190565b6000816000190483118215151615612747576127476126b4565b500290565b60008261276957634e487b7160e01b600052601260045260246000fd5b500490565b60006020828403121561278057600080fd5b81516113d681612497565b60005b838110156127a657818101518382015260200161278e565b83811115611fa25750506000910152565b600082516127c981846020870161278b565b9190910192915050565b60208152600082518060208401526127f281604085016020870161278b565b601f01601f1916919091016040019291505056fea2646970667358221220a35317482bdd824ae392fc837a8ebd80d30ad0350c2cc2d209910c66db3bc77964736f6c63430008090033