ETH Price: $3,435.75 (-0.35%)

Contract

0xd4829f126075603f562d84D670Dee1930456203e
 

Overview

ETH Balance

0.025108881773868255 ETH

ETH Value

$86.27 (@ $3,435.75/ETH)

Sponsored

Transaction Hash
Method
Block
From
To
Erc20Airdrop Cus...53760042024-06-28 8:03:4320 days ago1719561823IN
SlashToken: Drop 1.0
0.005 ETH0.000008620.01031092
Erc20Airdrop Cus...41205132024-05-30 6:34:0150 days ago1717050841IN
SlashToken: Drop 1.0
0.005 ETH0.00003370.01006353
Erc721Airdrop37829722024-05-22 11:02:3957 days ago1716375759IN
SlashToken: Drop 1.0
0.005 ETH0.000024620.01065738
Erc721Airdrop37829062024-05-22 11:00:2757 days ago1716375627IN
SlashToken: Drop 1.0
0.005 ETH0.000031870.01132695
Native Airdrop E...37459292024-05-21 14:27:5358 days ago1716301673IN
SlashToken: Drop 1.0
0.00506 ETH0.000004260.01717579
Initialize37424702024-05-21 12:32:3558 days ago1716294755IN
SlashToken: Drop 1.0
0 ETH0.000500491.02006303

Latest 7 internal transactions

Parent Transaction Hash Block From To
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37459292024-05-21 14:27:5358 days ago1716301673
SlashToken: Drop 1.0
0.00001 ETH
37424332024-05-21 12:31:2158 days ago1716294681  Contract Creation0 ETH

Loading...
Loading

Contract Source Code Verified (Exact Match)

Contract Name:
SlashTokenBlast

Compiler Version
v0.8.23+commit.f704f362

Optimization Enabled:
Yes with 9999999 runs

Other Settings:
paris EvmVersion
File 1 of 11 : SlashToken.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity 0.8.23;
// pragma solidity 0.8.19;
//import "@openzeppelin/contracts/security/ReentrancyGuard.sol"; @4.9.2 to get the same bytecode
import "../handshake-drop-libs/TokenTransferer.sol";
import "../handshake-drop-types/interfaces/SlashTokenEvents.sol";
import "../handshake-drop-libs/NativeTransferer.sol";
import "@openzeppelin/contracts/utils/ReentrancyGuard.sol";
import "../handshake-drop-libs/SubscriptionRegistry.sol";
/// @author 0xCocomastoras
/// @custom:version 1.0
/// @title SlashToken
/// @notice SlashToken is a simple, yet powerful tool to airdrop tokens and NFTs.

contract SlashTokenBlast is TokenTransferer, NativeTransferer, SlashTokenEvents, SubscriptionRegistry, ReentrancyGuard {

    constructor() ReentrancyGuard(){}

    /**
        @notice ERC-20 token airdrop with same, equal amount to all recipients
        @param recipients A list of addresses of the recipients
        @param amount Amount of tokens each recipient will be airdropped
        @param token Address of the token
    */
    function erc20AirdropEqualAmount(address[] calldata recipients, uint256 amount, address token) external payable nonReentrant {
        require(frozen == 0, "CF");
        require(denylist[msg.sender] == 0, 'UD');
        uint256 value = _getBaseFeeForWallet(); //Check if wallet is whitelisted with different value
        uint256 purchasedTxns = _getAvailableTxnsForWallet();
        uint recipientsLength = recipients.length;
        value = value == 0 ? baseFee : value;
        if (purchasedTxns == 0) {
            require(msg.value == value, "NVV");
        } else {
            _updateAvailableTxnsForWallet();
        }
        require(isInitialized != 0, 'NIY');
        require(recipientsLength <= 500, 'NVL');
        uint recipientsOffset;
        assembly {
            recipientsOffset := recipients.offset
        }
        _performMultiERC20Transfer(token, recipientsOffset, recipientsLength, amount);
        emit Erc20AirdropEqualAmount(msg.sender, token, recipientsLength, recipientsLength*amount);
    }

    /**
        @notice ERC-20 token airdrop with custom amount for each recipient
        @param recipients A list of addresses of the recipients
        @param amount A list of amounts of the tokens each recipient will be airdropped
        @param token Address of the token
        @param totalAmount The sum of all tokens to be airdropped
    */
    function erc20AirdropCustomAmount(address[] calldata recipients, uint256[] calldata amount, address token, uint256 totalAmount) external payable nonReentrant {
        require(frozen == 0, "CF");
        require(denylist[msg.sender] == 0, 'UD');
        uint256 value = _getBaseFeeForWallet(); //Check if wallet is whitelisted with different value
        uint256 purchasedTxns = _getAvailableTxnsForWallet();
        uint recipientsLength = recipients.length;
        value = value == 0 ? baseFee : value;
        if (purchasedTxns == 0) {
            require(msg.value == value, "NVV");
        } else {
            _updateAvailableTxnsForWallet();
        }
        require(isInitialized != 0, 'NIY');
        require(recipientsLength <= 500 && recipientsLength == amount.length, 'NVL');
        uint recipientsOffset;
        uint amountsOffset;

        assembly {
            recipientsOffset := recipients.offset
            amountsOffset := amount.offset
        }
        _performMultiERC20TransferCustom(token, recipientsOffset, recipientsLength, amountsOffset, totalAmount);
        emit Erc20AirdropCustomAmount(msg.sender, token, recipientsLength, totalAmount);
    }

    /**
        @notice Native currency airdrop with same, equal amount to all recipients
        @param recipients A list of addresses of the recipients
        @param amount Amount of tokens each recipient will be airdropped
    */
    function nativeAirdropEqualAmount(address[] calldata recipients, uint256 amount) external payable nonReentrant {
        require(frozen == 0, "CF");
        require(isInitialized != 0, 'NIY');
        require(denylist[msg.sender] == 0, 'UD');
        uint recipientsOffset;
        uint recipientsLength = recipients.length;
        uint256 value = _getBaseFeeForWallet();  //Check if wallet is whitelisted with different value
        uint256 purchasedTxns = _getAvailableTxnsForWallet();
        uint256 recipientsValue = amount * recipientsLength;
        value = value == 0 ? (baseFee + recipientsValue) : (value + recipientsValue);
        if (purchasedTxns == 0) {
            require(msg.value == value, "NVV");
        } else {
            require(msg.value == recipientsValue, 'NVV');
            _updateAvailableTxnsForWallet();
        }
        require(recipientsLength <= 500, 'NVL');
        assembly {
            recipientsOffset := recipients.offset
        }
        _performMultiNativeTransfer(recipientsOffset, recipientsLength, amount);
        emit NativeAirdropEqualAmount(msg.sender, recipientsLength, recipientsValue);
    }

    /**
        @notice Native currency airdrop with custom amount for each recipient
        @param recipients A list of addresses of the recipients
        @param amounts A list of amounts that each recipient will be airdropped
    */
    function nativeAirdropCustomAmount(address[] calldata recipients, uint256[] calldata amounts) external payable nonReentrant {
        require(frozen == 0, "CF");
        require(isInitialized != 0, 'NIY');
        require(denylist[msg.sender] == 0, 'UD');
        uint256 value = _getBaseFeeForWallet(); //Check if wallet is whitelisted with different value
        uint256 purchasedTxns = _getAvailableTxnsForWallet();
        uint recipientsOffset;
        uint amountsOffset;
        uint recipientsLength = recipients.length;
        require(recipientsLength <= 500 && recipientsLength == amounts.length, 'NVL');
        assembly {
            recipientsOffset := recipients.offset
            amountsOffset := amounts.offset
        }
        uint totalAmount = _performMultiNativeTransferCustom(recipientsOffset, recipientsLength, amountsOffset);
        value = value == 0 ? (baseFee + totalAmount) : (value + totalAmount);
        if (purchasedTxns == 0) {
            require(msg.value == value, "NVV");
        } else {
            require(msg.value == totalAmount, 'NVV');
            _updateAvailableTxnsForWallet();
        }
        emit NativeAirdropCustomAmount(msg.sender, recipientsLength, totalAmount);
    }

    /**
        @notice Basic Airdrop of Erc721 tokens without bundle
        @param recipients A list of addresses of the recipients
        @param ids A list of ids of the token each recipient will be airdropped
        @param token The address of the token
    */
    function erc721Airdrop(address[] calldata recipients, uint256[] calldata ids, address token) external payable nonReentrant {
        require(permitErc721 != 0, 'NEY');
        require(frozen == 0, "CF");
        require(isInitialized != 0, 'NIY');
        require(denylist[msg.sender] == 0, 'UD');
        uint256 value = _getBaseFeeForWallet();
        value = value == 0 ? baseFee : value;
        uint256 purchasedTxns = _getAvailableTxnsForWallet();
        uint recipientsLength = recipients.length;
        if (purchasedTxns == 0) {
            require(msg.value == value, "NVV");
        } else {
            _updateAvailableTxnsForWallet();
        }
        require(recipientsLength <= 500 && recipientsLength == ids.length, 'NVL');
        uint recipientsOffset;
        uint idsOffset;
        assembly {
            recipientsOffset := recipients.offset
            idsOffset := ids.offset
        }
        _performMultiERC721Transfer(token, msg.sender, recipientsOffset, recipientsLength, idsOffset);
        emit Erc721Airdrop(msg.sender, token, recipientsLength);
    }
}

File 2 of 11 : ReentrancyGuard.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/ReentrancyGuard.sol)

pragma solidity ^0.8.20;

/**
 * @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;

    /**
     * @dev Unauthorized reentrant call.
     */
    error ReentrancyGuardReentrantCall();

    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 making it call a
     * `private` function that does the actual work.
     */
    modifier nonReentrant() {
        _nonReentrantBefore();
        _;
        _nonReentrantAfter();
    }

    function _nonReentrantBefore() private {
        // On the first call to nonReentrant, _status will be NOT_ENTERED
        if (_status == ENTERED) {
            revert ReentrancyGuardReentrantCall();
        }

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

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

    /**
     * @dev Returns true if the reentrancy guard is currently set to "entered", which indicates there is a
     * `nonReentrant` function in the call stack.
     */
    function _reentrancyGuardEntered() internal view returns (bool) {
        return _status == ENTERED;
    }
}

File 3 of 11 : EnumerableSet.sol
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v5.0.0) (utils/structs/EnumerableSet.sol)
// This file was procedurally generated from scripts/generate/templates/EnumerableSet.js.

pragma solidity ^0.8.20;

/**
 * @dev Library for managing
 * https://en.wikipedia.org/wiki/Set_(abstract_data_type)[sets] of primitive
 * types.
 *
 * Sets have the following properties:
 *
 * - Elements are added, removed, and checked for existence in constant time
 * (O(1)).
 * - Elements are enumerated in O(n). No guarantees are made on the ordering.
 *
 * ```solidity
 * contract Example {
 *     // Add the library methods
 *     using EnumerableSet for EnumerableSet.AddressSet;
 *
 *     // Declare a set state variable
 *     EnumerableSet.AddressSet private mySet;
 * }
 * ```
 *
 * As of v3.3.0, sets of type `bytes32` (`Bytes32Set`), `address` (`AddressSet`)
 * and `uint256` (`UintSet`) are supported.
 *
 * [WARNING]
 * ====
 * Trying to delete such a structure from storage will likely result in data corruption, rendering the structure
 * unusable.
 * See https://github.com/ethereum/solidity/pull/11843[ethereum/solidity#11843] for more info.
 *
 * In order to clean an EnumerableSet, you can either remove all elements one by one or create a fresh instance using an
 * array of EnumerableSet.
 * ====
 */
library EnumerableSet {
    // To implement this library for multiple types with as little code
    // repetition as possible, we write it in terms of a generic Set type with
    // bytes32 values.
    // The Set implementation uses private functions, and user-facing
    // implementations (such as AddressSet) are just wrappers around the
    // underlying Set.
    // This means that we can only create new EnumerableSets for types that fit
    // in bytes32.

    struct Set {
        // Storage of set values
        bytes32[] _values;
        // Position is the index of the value in the `values` array plus 1.
        // Position 0 is used to mean a value is not in the set.
        mapping(bytes32 value => uint256) _positions;
    }

    /**
     * @dev Add a value to a set. O(1).
     *
     * Returns true if the value was added to the set, that is if it was not
     * already present.
     */
    function _add(Set storage set, bytes32 value) private returns (bool) {
        if (!_contains(set, value)) {
            set._values.push(value);
            // The value is stored at length-1, but we add 1 to all indexes
            // and use 0 as a sentinel value
            set._positions[value] = set._values.length;
            return true;
        } else {
            return false;
        }
    }

    /**
     * @dev Removes a value from a set. O(1).
     *
     * Returns true if the value was removed from the set, that is if it was
     * present.
     */
    function _remove(Set storage set, bytes32 value) private returns (bool) {
        // We cache the value's position to prevent multiple reads from the same storage slot
        uint256 position = set._positions[value];

        if (position != 0) {
            // Equivalent to contains(set, value)
            // To delete an element from the _values array in O(1), we swap the element to delete with the last one in
            // the array, and then remove the last element (sometimes called as 'swap and pop').
            // This modifies the order of the array, as noted in {at}.

            uint256 valueIndex = position - 1;
            uint256 lastIndex = set._values.length - 1;

            if (valueIndex != lastIndex) {
                bytes32 lastValue = set._values[lastIndex];

                // Move the lastValue to the index where the value to delete is
                set._values[valueIndex] = lastValue;
                // Update the tracked position of the lastValue (that was just moved)
                set._positions[lastValue] = position;
            }

            // Delete the slot where the moved value was stored
            set._values.pop();

            // Delete the tracked position for the deleted slot
            delete set._positions[value];

            return true;
        } else {
            return false;
        }
    }

    /**
     * @dev Returns true if the value is in the set. O(1).
     */
    function _contains(Set storage set, bytes32 value) private view returns (bool) {
        return set._positions[value] != 0;
    }

    /**
     * @dev Returns the number of values on the set. O(1).
     */
    function _length(Set storage set) private view returns (uint256) {
        return set._values.length;
    }

    /**
     * @dev Returns the value stored at position `index` in the set. O(1).
     *
     * Note that there are no guarantees on the ordering of values inside the
     * array, and it may change when more values are added or removed.
     *
     * Requirements:
     *
     * - `index` must be strictly less than {length}.
     */
    function _at(Set storage set, uint256 index) private view returns (bytes32) {
        return set._values[index];
    }

    /**
     * @dev Return the entire set in an array
     *
     * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
     * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
     * this function has an unbounded cost, and using it as part of a state-changing function may render the function
     * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
     */
    function _values(Set storage set) private view returns (bytes32[] memory) {
        return set._values;
    }

    // Bytes32Set

    struct Bytes32Set {
        Set _inner;
    }

    /**
     * @dev Add a value to a set. O(1).
     *
     * Returns true if the value was added to the set, that is if it was not
     * already present.
     */
    function add(Bytes32Set storage set, bytes32 value) internal returns (bool) {
        return _add(set._inner, value);
    }

    /**
     * @dev Removes a value from a set. O(1).
     *
     * Returns true if the value was removed from the set, that is if it was
     * present.
     */
    function remove(Bytes32Set storage set, bytes32 value) internal returns (bool) {
        return _remove(set._inner, value);
    }

    /**
     * @dev Returns true if the value is in the set. O(1).
     */
    function contains(Bytes32Set storage set, bytes32 value) internal view returns (bool) {
        return _contains(set._inner, value);
    }

    /**
     * @dev Returns the number of values in the set. O(1).
     */
    function length(Bytes32Set storage set) internal view returns (uint256) {
        return _length(set._inner);
    }

    /**
     * @dev Returns the value stored at position `index` in the set. O(1).
     *
     * Note that there are no guarantees on the ordering of values inside the
     * array, and it may change when more values are added or removed.
     *
     * Requirements:
     *
     * - `index` must be strictly less than {length}.
     */
    function at(Bytes32Set storage set, uint256 index) internal view returns (bytes32) {
        return _at(set._inner, index);
    }

    /**
     * @dev Return the entire set in an array
     *
     * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
     * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
     * this function has an unbounded cost, and using it as part of a state-changing function may render the function
     * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
     */
    function values(Bytes32Set storage set) internal view returns (bytes32[] memory) {
        bytes32[] memory store = _values(set._inner);
        bytes32[] memory result;

        /// @solidity memory-safe-assembly
        assembly {
            result := store
        }

        return result;
    }

    // AddressSet

    struct AddressSet {
        Set _inner;
    }

    /**
     * @dev Add a value to a set. O(1).
     *
     * Returns true if the value was added to the set, that is if it was not
     * already present.
     */
    function add(AddressSet storage set, address value) internal returns (bool) {
        return _add(set._inner, bytes32(uint256(uint160(value))));
    }

    /**
     * @dev Removes a value from a set. O(1).
     *
     * Returns true if the value was removed from the set, that is if it was
     * present.
     */
    function remove(AddressSet storage set, address value) internal returns (bool) {
        return _remove(set._inner, bytes32(uint256(uint160(value))));
    }

    /**
     * @dev Returns true if the value is in the set. O(1).
     */
    function contains(AddressSet storage set, address value) internal view returns (bool) {
        return _contains(set._inner, bytes32(uint256(uint160(value))));
    }

    /**
     * @dev Returns the number of values in the set. O(1).
     */
    function length(AddressSet storage set) internal view returns (uint256) {
        return _length(set._inner);
    }

    /**
     * @dev Returns the value stored at position `index` in the set. O(1).
     *
     * Note that there are no guarantees on the ordering of values inside the
     * array, and it may change when more values are added or removed.
     *
     * Requirements:
     *
     * - `index` must be strictly less than {length}.
     */
    function at(AddressSet storage set, uint256 index) internal view returns (address) {
        return address(uint160(uint256(_at(set._inner, index))));
    }

    /**
     * @dev Return the entire set in an array
     *
     * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
     * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
     * this function has an unbounded cost, and using it as part of a state-changing function may render the function
     * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
     */
    function values(AddressSet storage set) internal view returns (address[] memory) {
        bytes32[] memory store = _values(set._inner);
        address[] memory result;

        /// @solidity memory-safe-assembly
        assembly {
            result := store
        }

        return result;
    }

    // UintSet

    struct UintSet {
        Set _inner;
    }

    /**
     * @dev Add a value to a set. O(1).
     *
     * Returns true if the value was added to the set, that is if it was not
     * already present.
     */
    function add(UintSet storage set, uint256 value) internal returns (bool) {
        return _add(set._inner, bytes32(value));
    }

    /**
     * @dev Removes a value from a set. O(1).
     *
     * Returns true if the value was removed from the set, that is if it was
     * present.
     */
    function remove(UintSet storage set, uint256 value) internal returns (bool) {
        return _remove(set._inner, bytes32(value));
    }

    /**
     * @dev Returns true if the value is in the set. O(1).
     */
    function contains(UintSet storage set, uint256 value) internal view returns (bool) {
        return _contains(set._inner, bytes32(value));
    }

    /**
     * @dev Returns the number of values in the set. O(1).
     */
    function length(UintSet storage set) internal view returns (uint256) {
        return _length(set._inner);
    }

    /**
     * @dev Returns the value stored at position `index` in the set. O(1).
     *
     * Note that there are no guarantees on the ordering of values inside the
     * array, and it may change when more values are added or removed.
     *
     * Requirements:
     *
     * - `index` must be strictly less than {length}.
     */
    function at(UintSet storage set, uint256 index) internal view returns (uint256) {
        return uint256(_at(set._inner, index));
    }

    /**
     * @dev Return the entire set in an array
     *
     * WARNING: This operation will copy the entire storage to memory, which can be quite expensive. This is designed
     * to mostly be used by view accessors that are queried without any gas fees. Developers should keep in mind that
     * this function has an unbounded cost, and using it as part of a state-changing function may render the function
     * uncallable if the set grows to a point where copying to memory consumes too much gas to fit in a block.
     */
    function values(UintSet storage set) internal view returns (uint256[] memory) {
        bytes32[] memory store = _values(set._inner);
        uint256[] memory result;

        /// @solidity memory-safe-assembly
        assembly {
            result := store
        }

        return result;
    }
}

File 4 of 11 : ManagerActions.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

import "@openzeppelin/contracts/utils/structs/EnumerableSet.sol";
import {IBlast} from "../handshake-drop-types/interfaces/IBlast.sol";

contract ManagerActions{
    constructor(){}
    address owner;
    address feeSink;
    address gasSink;

    uint256 public frozen;
    uint256 public permitErc721 = 1;

    mapping(address => uint256) denylist;
    using EnumerableSet for EnumerableSet.AddressSet;
    EnumerableSet.AddressSet deniedAddresses;

    address constant internal YIELD_CONTRACT = 0x4300000000000000000000000000000000000002;


    /**
        @notice Admin freezes / unfreezes contracts
        @param value_ 0 = unfreeze, any other value = freeze
    */
    function freezeContract(uint256 value_) external {
        require(msg.sender == owner, 'NVS');
        frozen = value_;
    }

    /**
        @notice Admin permits/freezes erv721Airdrops
        @param value_ 0 = freeze, any other value = permit
    */
    function handleErc721Flag(uint256 value_) external {
        require(msg.sender == owner, 'NVS');
        permitErc721 = value_;
    }

    /**
        @notice Admin updates fee sink address
        @param feeSink_ The new fee sink address
    */
    function updateFeeSink(address feeSink_) external {
        require(msg.sender == owner, 'NVS');
        feeSink = feeSink_;
    }

    /**
        @notice Admin updates gas sink address
        @param gasSink_ The new gas sink address
    */
    function updateGasSink(address gasSink_) external {
        require(msg.sender == owner, 'NVS');
        gasSink = gasSink_;
    }

    function claimMaxGas() external {
        require(msg.sender == owner, 'NVS');
        IBlast(YIELD_CONTRACT).claimMaxGas(address(this), gasSink);
    }

    /**
        @notice Admin claims contract fees
    */
    function claimFees() external {
        address owner_ = owner;
        assembly {
            if iszero(eq(caller(), owner_)) {
                revert(0,0)
            }
            if iszero(call(gas(), sload(feeSink.slot), selfbalance(), 0, 0, 0, 0)) {
                revert(0,0)
            }
        }
    }

    function addToDenylist(address[] memory list) external {
        require(msg.sender == owner, 'NVS');
        uint len = list.length;
        for(uint i = 0; i < len;) {
            if (!deniedAddresses.contains(list[i])) {
                deniedAddresses.add(list[i]);
            }
            unchecked {
                denylist[list[i]] = 1;
                i++;
            }
        }
    }

    function removeFromDenylist(address[] memory list) external {
        require(msg.sender == owner, 'NVS');
        uint len = list.length;
        for(uint i = 0; i < len;) {
            if (deniedAddresses.contains(list[i])) {
                deniedAddresses.remove(list[i]);
            }
            unchecked {
                denylist[list[i]] = 0;
                i++;
            }
        }
    }

    function getDenylist() external view returns (address[] memory) {
        require(msg.sender == owner, 'NVS');
        return deniedAddresses.values();
    }
}

File 5 of 11 : NativeTransferer.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;


contract NativeTransferer {
    uint256 internal constant GAS_STIPEND_NO_STORAGE_WRITES = 2300;

    /**
     * @dev Internal function to transfer native tokens from a given originator
     *      to a multiple recipients
     *
     * @param offset     Calldata offset of the recipients of the transfer.
     * @param length     Calldata length of the recipients of the transfer.
     * @param amount     The amount to transfer.
     */
    function _performMultiNativeTransfer(uint256 offset, uint256 length, uint256 amount) internal {
        assembly {
             for { let i := 0 } lt(i, length) { i := add(i, 1) } {
                 let to := calldataload(add(offset, mul(i, 0x20)))
                 if iszero( call(
                    GAS_STIPEND_NO_STORAGE_WRITES,
                    to,
                    amount,
                    0,
                    0,
                    0,
                    0
                 )) {
                     revert(0,0)
                 }
             }
        }
    }

    /**
     * @dev Internal function to transfer native tokens from a given originator
     *      to a multiple recipients
     *
     * @param recipientsOffset            Calldata offset of the recipients of the transfer.
     * @param length            Calldata length of the recipients of the transfer.
     * @param amountsOffset     Calldata offset of the amounts to transfer
     */
    function _performMultiNativeTransferCustom(uint256 recipientsOffset, uint256 length, uint256 amountsOffset) internal returns (uint256 totalAmount){
        assembly {
             for { let i := 0 } lt(i, length) { i := add(i, 1) } {
                 let to := calldataload(add(recipientsOffset, mul(i, 0x20)))
                 let amount := calldataload(add(amountsOffset, mul(i, 0x20)))
                 totalAmount := add(totalAmount, amount)
                 if iszero( call(
                    GAS_STIPEND_NO_STORAGE_WRITES,
                    to,
                    amount,
                    0,
                    0,
                    0,
                    0
                 )) {
                     revert(0,0)
                 }
             }
        }
    }
}

File 6 of 11 : SubscriptionRegistry.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

import "../handshake-drop-types/interfaces/SlashTokenRegistryEvents.sol";
import "../handshake-drop-types/interfaces/PremiumSubscriptionRegistryEvents.sol";
import "./ManagerActions.sol";
import {IBlastPoints} from "../handshake-drop-types/interfaces/IBlast.sol";

contract SubscriptionRegistry is SlashTokenRegistryEvents, PremiumSubscriptionRegistryEvents, ManagerActions {
    // @dev user's adddress to custom base fee for no bundle purchases
    mapping (address => uint256) baseFeeWhitelisted;
    // @dev user address to total available txns to use
    mapping(address => uint256) public userToTxns;

    uint256[] availableTxnsBundles;
    uint256[] txnsBundlesToPrice;

    uint256 isInitialized;
    uint256 public baseFee;
    using EnumerableSet for EnumerableSet.AddressSet;
    EnumerableSet.AddressSet bundleUsers;

    address constant internal POINTS_CONTRACT = 0x2536FE9ab3F511540F2f9e2eC2A805005C3Dd800;


    function initialize(address admin_, address feeSink_, address gasSink_, uint256 baseFeeCostInWei, uint256[] memory availableTxnsBundles_, uint256[] memory txnsBundlesToPrice_ ) external {
        require(isInitialized == 0, 'AI');
        require(availableTxnsBundles_.length == txnsBundlesToPrice_.length, 'NVD');
        owner = admin_;
        feeSink = feeSink_;
        gasSink = gasSink_;
        availableTxnsBundles = availableTxnsBundles_;
        txnsBundlesToPrice = txnsBundlesToPrice_;
        isInitialized = 1;
        baseFee = baseFeeCostInWei;
        IBlast(YIELD_CONTRACT).configureAutomaticYield();
        IBlast(YIELD_CONTRACT).configureClaimableGas();
        IBlastPoints(POINTS_CONTRACT).configurePointsOperator(admin_);
    }

    constructor(){}

    /**
        @notice User buys a bundle of txns
        @param bundleIndex The index of the bundle array
        @param quantity The number of bundles that the user wants to buy
    */
    function buyTxnsBundle(uint256 bundleIndex, uint256 quantity) external payable {
        require(frozen == 0, "CF");
        require(msg.value == txnsBundlesToPrice[bundleIndex] * quantity, 'NVV');
        require(denylist[msg.sender] == 0, 'UD');
        require(quantity != 0, 'NVA');
        if(!bundleUsers.contains(msg.sender)) {
            bundleUsers.add(msg.sender);
        }
        uint256 total;
        unchecked {
            total = availableTxnsBundles[bundleIndex] * quantity;
            userToTxns[msg.sender] += total;
        }
        emit TxnsBundleBought(msg.sender, msg.value, total);
    }

    /**
        @notice Admin sets promo fee for wallet instead of default base fee
        @param wallet User's wallet address
        @param amountInWei New cost per txns
    */
    function setBaseFeeForWallet(address wallet, uint256 amountInWei) external {
        require(amountInWei < baseFee, "NVV");
        require(msg.sender == owner, 'NVS');
        baseFeeWhitelisted[wallet] = amountInWei;
        emit WalletBaseFeeSet(wallet, amountInWei);
    }

    /**
        @notice Admin resets promo fee for wallet. Default base fee applies
        @param wallet User's wallet address
    */
    function resetBaseFeeForWallet(address wallet) external {
        require(msg.sender == owner, 'NVS');
        delete baseFeeWhitelisted[wallet];
        emit WalletBaseFeeReset(wallet);
    }

    /**
        @notice Admin adds txns to a user
        @param wallets A list of user's wallet address
        @param txns A list of txns to be added
    */
    function addTxnsToWallets(address[] memory wallets, uint256[] memory txns) external {
        require(msg.sender == owner, 'NVS');
        require(wallets.length == txns.length, "NVL");
        uint len = wallets.length;
        for(uint i =0; i<len;){
            unchecked {
                userToTxns[wallets[i]] += txns[i];
                i++;
            }
        }
        emit TxnsAdded(wallets, txns);
    }

    /**
        @notice Admin sets the new base fee for all txns
        @param baseFee_ New base fee
    */
    function setNewBaseFee(uint256 baseFee_) external {
        require(msg.sender == owner, 'NVS');
        baseFee = baseFee_;
    }

    /**
        @notice Admin sets the new available txnsBundles and prices
        @param availableTxnsBundles_ New available bundles
        @param txnsBundlesToPrice_ New price per bundles
    */
    function updateBundles(uint256[] memory availableTxnsBundles_, uint256[] memory txnsBundlesToPrice_ ) external {
        require(msg.sender == owner, 'NVS');
        require(availableTxnsBundles_.length == txnsBundlesToPrice_.length, 'NVD');
        availableTxnsBundles = availableTxnsBundles_;
        txnsBundlesToPrice = txnsBundlesToPrice_;
        emit BundlesUpdated(msg.sender, availableTxnsBundles_, txnsBundlesToPrice_);
    }

    /**
        @notice External view function that returns active bundle offers
    */
    function getBundles() external view returns (uint256[] memory AvailableBundles, uint256[] memory BundlesPrices) {
        AvailableBundles = availableTxnsBundles;
        BundlesPrices = txnsBundlesToPrice;
    }

    /**
        @notice External view function that returns the custom base fee for wallet
    */
    function getBaseFeeForWallet() external view returns (uint256) {
        return baseFeeWhitelisted[msg.sender];
    }

    /**
        @notice External view function that returns the available txns for wallet
    */
    function getAvailableTxnsForWallet() external view returns (uint256) {
        return userToTxns[msg.sender];
    }

    /**
        @notice External view function that returns all the users that have bought a bundle
    */
    function getUsersThatBoughtBundles() external view returns (address[] memory Users) {
        require(msg.sender == owner, 'NVS');
        Users = bundleUsers.values();
    }

    /**
        @notice Internal view function that returns the custom base fee for wallet
    */
    function _getBaseFeeForWallet() internal view returns (uint256) {
        return baseFeeWhitelisted[msg.sender];
    }

    /**
        @notice Internal view function that returns the available txns for wallet
    */
    function _updateAvailableTxnsForWallet() internal {
        unchecked {
            --userToTxns[msg.sender];
        }
    }

    /**
        @notice Internal view function that returns the available txns for wallet
    */
    function _getAvailableTxnsForWallet() internal view returns (uint256) {
        return userToTxns[msg.sender];
    }
}

File 7 of 11 : TokenTransferer.sol
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.13;

/// @notice Safe ERC20 ,ERC721 multi transfer library that gracefully handles missing return values.
/// @author Cocomastoras
/// @author Modified from Solady (https://github.com/vectorized/solady/blob/main/src/utils/SafeTransferLib.sol)
/// @author Modified from Solmate (https://github.com/transmissions11/solmate/blob/main/src/utils/SafeTransferLib.sol)
///
/// @dev Note:
/// - For ERC20s and ERC721s, this implementation won't check that a token has code,
/// responsibility is delegated to the caller.

contract TokenTransferer {
    error TransferFromFailed();

    /**
     * @dev Internal function to transfer ERC20 tokens from a given originator
     *      to a multiple recipients. Sufficient approvals must be set on the
     *      contract performing the transfer.
     *
     * @param token                The ERC20 token to transfer.
     * @param recipientsOffset     Calldata offset of the recipients of the transfer.
     * @param length               Calldata length of the recipients of the transfer.
     * @param amount               The amount to transfer.
     */
    function _performMultiERC20Transfer(address token, uint256 recipientsOffset, uint256 length, uint256 amount) internal{
        /// @solidity memory-safe-assembly
        assembly {
            let total := mul(amount, length)
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x60, total) // Store the `amount` argument.
            mstore(0x40, address()) // Store the `to` argument.
            mstore(0x2c, shl(96, caller())) // Store the `from` argument.
            mstore(0x0c, 0x23b872dd000000000000000000000000)
            if iszero(
                and( // The arguments of `and` are evaluated from right to left.
                    or(
                        eq(mload(0x00), 1), iszero(returndatasize())), // Returned 1 or nothing.
                        call(gas(), token, 0, 0x1c, 0x64, 0x00, 0x20)
                    )
                )
            {
                mstore(0x00, 0x7939f424) // `TransferFromFailed()`.
                revert(0x1c, 0x04)
            }
            mstore(0x40, amount) // Store the `amount` argument.
            for { let i := 0 } lt(i, length) { i := add(i, 1) } {
                let to := calldataload(add(recipientsOffset, mul(i, 0x20)))
                mstore(0x2c, shl(96, to)) // Store the `to` argument.
                mstore(0x0c, 0xa9059cbb000000000000000000000000) // `transfer(address,uint256)`.
                // Perform the transfer, reverting upon failure.
                if iszero(
                    and( // The arguments of `and` are evaluated from right to left.
                        or(eq(mload(0x00), 1), iszero(returndatasize())), // Returned 1 or nothing.
                        call(gas(), token, 0, 0x1c, 0x44, 0x00, 0x20)
                    )
                ) {
                    mstore(0x00, 0x7939f424) // `TransferFromFailed()`.
                    revert(0x1c, 0x04)
                }
            }
            mstore(0x60, 0) // Restore the zero slot to zero.
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /**
        * @dev Internal function to transfer ERC20 tokens from a given originator
        *      to multiple recipients. Sufficient approvals must be set on the
        *      contract performing the transfer.
        * @param token            The ERC20 token to transfer.
        * @param recipientsOffset Offset of the recipients of the transfer.
        * @param recipientsLength Length of the recipients of the transfer.
        * @param amountsOffset    Offset of the amounts to transfer.
        * @param totalAmount      The totalAmount to transfer
    */
    function _performMultiERC20TransferCustom(address token, uint256 recipientsOffset, uint256 recipientsLength, uint256 amountsOffset, uint256 totalAmount) internal {
        /// @solidity memory-safe-assembly
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            mstore(0x60, totalAmount) // Store the `amount` argument.
            mstore(0x40, address()) // Store the `to` argument.
            mstore(0x2c, shl(96, caller())) // Store the `from` argument.
            mstore(0x0c, 0x23b872dd000000000000000000000000)
            if iszero(
                and( // The arguments of `and` are evaluated from right to left.
                    or(
                        eq(mload(0x00), 1), iszero(returndatasize())), // Returned 1 or nothing.
                        call(gas(), token, 0, 0x1c, 0x64, 0x00, 0x20)
                    )
                )
            {
                mstore(0x00, 0x7939f424) // `TransferFromFailed()`.
                revert(0x1c, 0x04)
            }
            let sumAmount := 0
            for { let i := 0 } lt(i, recipientsLength) { i := add(i, 1) } {
                let to := calldataload(add(recipientsOffset, mul(i, 0x20)))
                let amount := calldataload(add(amountsOffset, mul(i, 0x20)))
                sumAmount := add(sumAmount, amount)
                mstore(0x40, amount) // Store the `amount` argument.
                mstore(0x2c, shl(96, to)) // Store the `to` argument.
                mstore(0x0c, 0xa9059cbb000000000000000000000000) // `transfer(address,uint256)`.
                // Perform the transfer, reverting upon failure.
                if iszero(
                    and( // The arguments of `and` are evaluated from right to left.
                        or(eq(mload(0x00), 1), iszero(returndatasize())), // Returned 1 or nothing.
                        call(gas(), token, 0, 0x1c, 0x44, 0x00, 0x20)
                    )
                ) {
                    mstore(0x00, 0x7939f424) // `TransferFromFailed()`.
                    revert(0x1c, 0x04)
                }
            }
            if iszero(eq(totalAmount, sumAmount)) {
                revert(0,0)
            }
            mstore(0x60, 0) // Restore the zero slot to zero.
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }

    /**
     * @dev Internal function to transfer batch of ERC721 tokens from a given
     *      originator to multiple recipients. Sufficient approvals must be set on
     *      the contract performing the transfer. Note that this function does
     *      not check whether the receiver can accept the ERC721 token (i.e. it
     *      does not use `safeTransferFrom`).
     *
     * @param token             The ERC721 token to transfer.
     * @param from              The originator of the transfer.
     * @param recipientsOffset  The offset of recipients of the transfer.
     * @param recipientsLength  The length of tokens to transfer.
     * @param idsOffset         The offset of tokenIds to transfer.
     */
    function _performMultiERC721Transfer(
        address token,
        address from,
        uint256 recipientsOffset,
        uint256 recipientsLength,
        uint256 idsOffset
    ) internal {
        // Utilize assembly to perform an optimized ERC721 token transfer.
        assembly {
            let m := mload(0x40) // Cache the free memory pointer.
            for { let i := 0 } lt(i, recipientsLength) { i := add(i, 1) } {
                let to := calldataload(add(recipientsOffset, mul(i, 0x20)))
                let identifier := calldataload(add(idsOffset, mul(i, 0x20)))
                mstore(0x60, identifier) // Store the `identifier` argument.
                mstore(0x40, to) // Store the `to` argument.
                mstore(0x2c, shl(96, from)) // Store the `from` argument.
                mstore(0x0c, 0x23b872dd000000000000000000000000) // `transferFrom(address,address,uint256)`.
                // Perform the transfer, reverting upon failure.
                if iszero(
                    and( // The arguments of `and` are evaluated from right to left.
                        iszero(returndatasize()), // Returned error.
                        call(gas(), token, 0, 0x1c, 0x64, 0x00, 0x00)
                    )
                ) {
                    mstore(0x00, 0x7939f424) // `TransferFromFailed()`.
                    revert(0x1c, 0x04)
                }
            }
            mstore(0x60, 0) // Restore the zero slot to zero.
            mstore(0x40, m) // Restore the free memory pointer.
        }
    }
}

File 8 of 11 : IBlast.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

enum YieldMode {
    AUTOMATIC,
    VOID,
    CLAIMABLE
}

enum GasMode {
    VOID,
    CLAIMABLE
}

interface IBlast{
    // configure
    function configureContract(address contractAddress, YieldMode _yield, GasMode gasMode, address governor) external;
    function configure(YieldMode _yield, GasMode gasMode, address governor) external;

    // base configuration options
    function configureClaimableYield() external;
    function configureClaimableYieldOnBehalf(address contractAddress) external;
    function configureAutomaticYield() external;
    function configureAutomaticYieldOnBehalf(address contractAddress) external;
    function configureVoidYield() external;
    function configureVoidYieldOnBehalf(address contractAddress) external;
    function configureClaimableGas() external;
    function configureClaimableGasOnBehalf(address contractAddress) external;
    function configureVoidGas() external;
    function configureVoidGasOnBehalf(address contractAddress) external;
    function configureGovernor(address _governor) external;
    function configureGovernorOnBehalf(address _newGovernor, address contractAddress) external;

    // claim yield
    function claimYield(address contractAddress, address recipientOfYield, uint256 amount) external returns (uint256);
    function claimAllYield(address contractAddress, address recipientOfYield) external returns (uint256);

    // claim gas
    function claimAllGas(address contractAddress, address recipientOfGas) external returns (uint256);
    function claimGasAtMinClaimRate(address contractAddress, address recipientOfGas, uint256 minClaimRateBips) external returns (uint256);
    function claimMaxGas(address contractAddress, address recipientOfGas) external returns (uint256);
    function claimGas(address contractAddress, address recipientOfGas, uint256 gasToClaim, uint256 gasSecondsToConsume) external returns (uint256);

    // read functions
    function readClaimableYield(address contractAddress) external view returns (uint256);
    function readYieldConfiguration(address contractAddress) external view returns (uint8);
    function readGasParams(address contractAddress) external view returns (uint256 etherSeconds, uint256 etherBalance, uint256 lastUpdated, GasMode);
}

interface IBlastPoints {
  function configurePointsOperator(address operator) external;
  function configurePointsOperatorOnBehalf(address contractAddress, address operator) external;
}

File 9 of 11 : PremiumSubscriptionRegistryEvents.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

interface PremiumSubscriptionRegistryEvents {
    event WalletBaseFeeSet(address indexed Wallet, uint256 BaseFeeInWei);
    event WalletBaseFeeReset(address indexed Wallet);
    event TxnsAdded(address[] Wallet, uint256[] Txns);
}

File 10 of 11 : SlashTokenEvents.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

interface SlashTokenEvents {
    event Erc20AirdropEqualAmount(address indexed From, address indexed Token,uint256 RecipientsLength, uint256 TotalAmount);
    event Erc20AirdropCustomAmount(address indexed From, address indexed Token, uint256 RecipientsLength, uint256 TotalAmount);
    event NativeAirdropEqualAmount(address indexed From,uint256 RecipientsLength, uint256 TotalAmount);
    event NativeAirdropCustomAmount(address indexed From, uint256 RecipientsLength, uint256 TotalAmount);
    event Erc721Airdrop(address indexed From, address indexed Token, uint256 RecipientsLength);
}

File 11 of 11 : SlashTokenRegistryEvents.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.0;

interface SlashTokenRegistryEvents {
    event TxnsBundleBought(address indexed Buyer, uint256 Amount, uint256 Txns);
    event BundlesUpdated(address indexed Operator, uint256[] BundlesAmounts, uint256[] BundlesPrices);
}

Settings
{
  "optimizer": {
    "enabled": true,
    "runs": 9999999
  },
  "evmVersion": "paris",
  "outputSelection": {
    "*": {
      "*": [
        "evm.bytecode",
        "evm.deployedBytecode",
        "devdoc",
        "userdoc",
        "metadata",
        "abi"
      ]
    }
  },
  "libraries": {}
}

Contract Security Audit

Contract ABI

[{"inputs":[],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ReentrancyGuardReentrantCall","type":"error"},{"inputs":[],"name":"TransferFromFailed","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"Operator","type":"address"},{"indexed":false,"internalType":"uint256[]","name":"BundlesAmounts","type":"uint256[]"},{"indexed":false,"internalType":"uint256[]","name":"BundlesPrices","type":"uint256[]"}],"name":"BundlesUpdated","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"From","type":"address"},{"indexed":true,"internalType":"address","name":"Token","type":"address"},{"indexed":false,"internalType":"uint256","name":"RecipientsLength","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"TotalAmount","type":"uint256"}],"name":"Erc20AirdropCustomAmount","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"From","type":"address"},{"indexed":true,"internalType":"address","name":"Token","type":"address"},{"indexed":false,"internalType":"uint256","name":"RecipientsLength","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"TotalAmount","type":"uint256"}],"name":"Erc20AirdropEqualAmount","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"From","type":"address"},{"indexed":true,"internalType":"address","name":"Token","type":"address"},{"indexed":false,"internalType":"uint256","name":"RecipientsLength","type":"uint256"}],"name":"Erc721Airdrop","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"From","type":"address"},{"indexed":false,"internalType":"uint256","name":"RecipientsLength","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"TotalAmount","type":"uint256"}],"name":"NativeAirdropCustomAmount","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"From","type":"address"},{"indexed":false,"internalType":"uint256","name":"RecipientsLength","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"TotalAmount","type":"uint256"}],"name":"NativeAirdropEqualAmount","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address[]","name":"Wallet","type":"address[]"},{"indexed":false,"internalType":"uint256[]","name":"Txns","type":"uint256[]"}],"name":"TxnsAdded","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"Buyer","type":"address"},{"indexed":false,"internalType":"uint256","name":"Amount","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"Txns","type":"uint256"}],"name":"TxnsBundleBought","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"Wallet","type":"address"}],"name":"WalletBaseFeeReset","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"Wallet","type":"address"},{"indexed":false,"internalType":"uint256","name":"BaseFeeInWei","type":"uint256"}],"name":"WalletBaseFeeSet","type":"event"},{"inputs":[{"internalType":"address[]","name":"list","type":"address[]"}],"name":"addToDenylist","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"wallets","type":"address[]"},{"internalType":"uint256[]","name":"txns","type":"uint256[]"}],"name":"addTxnsToWallets","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"baseFee","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"bundleIndex","type":"uint256"},{"internalType":"uint256","name":"quantity","type":"uint256"}],"name":"buyTxnsBundle","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"claimFees","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"claimMaxGas","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"amount","type":"uint256[]"},{"internalType":"address","name":"token","type":"address"},{"internalType":"uint256","name":"totalAmount","type":"uint256"}],"name":"erc20AirdropCustomAmount","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256","name":"amount","type":"uint256"},{"internalType":"address","name":"token","type":"address"}],"name":"erc20AirdropEqualAmount","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"ids","type":"uint256[]"},{"internalType":"address","name":"token","type":"address"}],"name":"erc721Airdrop","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"uint256","name":"value_","type":"uint256"}],"name":"freezeContract","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"frozen","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getAvailableTxnsForWallet","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getBaseFeeForWallet","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getBundles","outputs":[{"internalType":"uint256[]","name":"AvailableBundles","type":"uint256[]"},{"internalType":"uint256[]","name":"BundlesPrices","type":"uint256[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getDenylist","outputs":[{"internalType":"address[]","name":"","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"getUsersThatBoughtBundles","outputs":[{"internalType":"address[]","name":"Users","type":"address[]"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"value_","type":"uint256"}],"name":"handleErc721Flag","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"admin_","type":"address"},{"internalType":"address","name":"feeSink_","type":"address"},{"internalType":"address","name":"gasSink_","type":"address"},{"internalType":"uint256","name":"baseFeeCostInWei","type":"uint256"},{"internalType":"uint256[]","name":"availableTxnsBundles_","type":"uint256[]"},{"internalType":"uint256[]","name":"txnsBundlesToPrice_","type":"uint256[]"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256[]","name":"amounts","type":"uint256[]"}],"name":"nativeAirdropCustomAmount","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"recipients","type":"address[]"},{"internalType":"uint256","name":"amount","type":"uint256"}],"name":"nativeAirdropEqualAmount","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"permitErc721","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address[]","name":"list","type":"address[]"}],"name":"removeFromDenylist","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"}],"name":"resetBaseFeeForWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"wallet","type":"address"},{"internalType":"uint256","name":"amountInWei","type":"uint256"}],"name":"setBaseFeeForWallet","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"baseFee_","type":"uint256"}],"name":"setNewBaseFee","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256[]","name":"availableTxnsBundles_","type":"uint256[]"},{"internalType":"uint256[]","name":"txnsBundlesToPrice_","type":"uint256[]"}],"name":"updateBundles","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"feeSink_","type":"address"}],"name":"updateFeeSink","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"gasSink_","type":"address"}],"name":"updateGasSink","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"userToTxns","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"}]

6080604052600160045534801561001557600080fd5b5060016010556136918061002a6000396000f3fe6080604052600436106101c25760003560e01c80636ef25c3a116100f757806393f9e6f911610095578063d294f09311610064578063d294f09314610483578063d993cdff14610498578063e85ddb8a146104c5578063fe700990146104e557600080fd5b806393f9e6f914610423578063b2b8c93f14610438578063bd3b819f1461044d578063cddfa1a41461046d57600080fd5b80638634fd24116100d15780638634fd24146103ca57806388f941e8146103dd5780638a6ff456146103f05780638fc8b3b21461041057600080fd5b80636ef25c3a146103725780637850953d14610388578063798ed83d146103aa57600080fd5b806334ae8e3811610164578063586668061161013e578063586668061461031957806362274c2b1461032c5780636b55040f1461034c5780636c11d85a1461035f57600080fd5b806334ae8e38146102b757806347ec4ed1146102d7578063527d9730146102f957600080fd5b8063244bd967116101a0578063244bd96714610235578063286ddb681461025757806331fd0d7e1461027757806333f740a11461029757600080fd5b8063054f7d9c146101c757806320a225cb146101f057806322f10e2f14610213575b600080fd5b3480156101d357600080fd5b506101dd60035481565b6040519081526020015b60405180910390f35b3480156101fc57600080fd5b50610205610505565b6040516101e7929190612edc565b34801561021f57600080fd5b5061023361022e366004612f0a565b6105b2565b005b34801561024157600080fd5b50336000908152600960205260409020546101dd565b34801561026357600080fd5b50610233610272366004612f0a565b61063d565b34801561028357600080fd5b50610233610292366004612f0a565b6106c3565b3480156102a357600080fd5b506102336102b2366004612f4c565b610749565b3480156102c357600080fd5b506102336102d2366004613087565b61089b565b3480156102e357600080fd5b50336000908152600860205260409020546101dd565b34801561030557600080fd5b506102336103143660046130eb565b6109f7565b6102336103273660046131d5565b610cec565b34801561033857600080fd5b50610233610347366004613241565b61107b565b61023361035a36600461325c565b61114d565b61023361036d3660046132e5565b611471565b34801561037e57600080fd5b506101dd600d5481565b34801561039457600080fd5b5061039d611809565b6040516101e791906133ad565b3480156103b657600080fd5b506102336103c5366004613426565b61189c565b6102336103d8366004613463565b6119e0565b6102336103eb3660046134c0565b611cf7565b3480156103fc57600080fd5b5061023361040b366004613426565b611f6c565b61023361041e3660046134e2565b612094565b34801561042f57600080fd5b5061039d61242f565b34801561044457600080fd5b506102336124bd565b34801561045957600080fd5b50610233610468366004613241565b6125ef565b34801561047957600080fd5b506101dd60045481565b34801561048f57600080fd5b506102336126b7565b3480156104a457600080fd5b506101dd6104b3366004613241565b60096020526000908152604090205481565b3480156104d157600080fd5b506102336104e036600461352e565b6126f1565b3480156104f157600080fd5b50610233610500366004613241565b612898565b606080600a80548060200260200160405190810160405280929190818152602001828054801561055457602002820191906000526020600020905b815481526020019060010190808311610540575b50505050509150600b8054806020026020016040519081016040528092919081815260200182805480156105a757602002820191906000526020600020905b815481526020019060010190808311610593575b505050505090509091565b60005473ffffffffffffffffffffffffffffffffffffffff163314610638576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e5653000000000000000000000000000000000000000000000000000000000060448201526064015b60405180910390fd5b600d55565b60005473ffffffffffffffffffffffffffffffffffffffff1633146106be576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600355565b60005473ffffffffffffffffffffffffffffffffffffffff163314610744576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600455565b600d5481106107b4576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b60005473ffffffffffffffffffffffffffffffffffffffff163314610835576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b73ffffffffffffffffffffffffffffffffffffffff821660008181526008602052604090819020839055517f44784c405393a593553ed0bf0ddb15aa2494ba9b97a8d75dfc9fabb7a64c8ce59061088f9084815260200190565b60405180910390a25050565b60005473ffffffffffffffffffffffffffffffffffffffff16331461091c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8051825114610987576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56440000000000000000000000000000000000000000000000000000000000604482015260640161062f565b815161099a90600a906020850190612e40565b5080516109ae90600b906020840190612e40565b503373ffffffffffffffffffffffffffffffffffffffff167fed68a7a2289c86234d260dc96066680ff0bcde7d3376a219df515dde860435b1838360405161088f929190612edc565b600c5415610a61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4149000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8051825114610acc576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56440000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6000805473ffffffffffffffffffffffffffffffffffffffff8089167fffffffffffffffffffffffff0000000000000000000000000000000000000000928316179092556001805488841690831617905560028054928716929091169190911790558151610b4190600a906020850190612e40565b508051610b5590600b906020840190612e40565b506001600c55600d839055604080517f7114177a000000000000000000000000000000000000000000000000000000008152905173430000000000000000000000000000000000000291637114177a91600480830192600092919082900301818387803b158015610bc557600080fd5b505af1158015610bd9573d6000803e3d6000fd5b5050505073430000000000000000000000000000000000000273ffffffffffffffffffffffffffffffffffffffff16634e606c476040518163ffffffff1660e01b8152600401600060405180830381600087803b158015610c3957600080fd5b505af1158015610c4d573d6000803e3d6000fd5b50506040517f36b91f2b00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff89166004820152732536fe9ab3f511540f2f9e2ec2a805005c3dd80092506336b91f2b9150602401600060405180830381600087803b158015610ccc57600080fd5b505af1158015610ce0573d6000803e3d6000fd5b50505050505050505050565b610cf4612960565b60035415610d5e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c54600003610dca576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415610e41576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b336000908152600860209081526040808320546009909252822054909180866101f48111801590610e7157508086145b610ed7576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8892508691506000610eea8483856129a3565b90508515610f0157610efc8187613594565b610f0f565b80600d54610f0f9190613594565b955084600003610f8757853414610f82576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61102a565b803414610ff0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61102a33600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b604080518381526020810183905233917f2c7cd2d52efdb7bcb324ce1fdaad584211503edbbf94fa7a3fde2624da572642910160405180910390a25050505050506110756001601055565b50505050565b60005473ffffffffffffffffffffffffffffffffffffffff1633146110fc576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b73ffffffffffffffffffffffffffffffffffffffff8116600081815260086020526040808220829055517f9a93cb5054fe47b6e8ec0e29a26edd6249309d823eccab337b5c81dda65f6ddc9190a250565b611155612960565b600354156111bf576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611236576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526008602090815260408083205460099092529091205486821561125f5782611263565b600d545b9250816000036112db578234146112d6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611315565b61131533600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b600c54600003611381576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6101f4811115801561139257508086145b6113f8576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8887611407878385848a6129e6565b604080518481526020810188905273ffffffffffffffffffffffffffffffffffffffff89169133917f0e18fd6025578556afc2d4c83f1e98be2ddb206457774fa37a3a8b1605ad6f79910160405180910390a350505050506114696001601055565b505050505050565b611479612960565b6004546000036114e5576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e45590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6003541561154f576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c546000036115bb576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611632576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260086020526040902054801561164e5780611652565b600d545b9050600061166c3360009081526009602052604090205490565b90508560008290036116e6578234146116e1576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611720565b61172033600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b6101f4811115801561173157508085145b611797576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b87866117a68633848685612abd565b60405183815273ffffffffffffffffffffffffffffffffffffffff87169033907f4bd386a75bd69ced877c29ffb9d2058eeed770d425c9027116b45e6f0fb4645a9060200160405180910390a350505050506118026001601055565b5050505050565b60005460609073ffffffffffffffffffffffffffffffffffffffff16331461188d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611897600e612b21565b905090565b60005473ffffffffffffffffffffffffffffffffffffffff16331461191d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b805160005b818110156119db5761195783828151811061193f5761193f6135a7565b60200260200101516006612b3590919063ffffffff16565b61198a57611988838281518110611970576119706135a7565b60200260200101516006612b6990919063ffffffff16565b505b6001600560008584815181106119a2576119a26135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff16825281019190915260400160002055600101611922565b505050565b6119e8612960565b60035415611a52576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611ac9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260086020908152604080832054600990925290912054848215611af25782611af6565b600d545b925081600003611b6e57823414611b69576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611ba8565b611ba833600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b600c54600003611c14576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6101f4811115611c80576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b86611c8d85828489612b8b565b73ffffffffffffffffffffffffffffffffffffffff8516337fbfc5bd893849e5d9bf1ac87d7e1fcec4f9afece75f87062d0c2370f1c6b5734b84611cd18a826135d6565b6040805192835260208301919091520160405180910390a3505050506110756001601055565b60035415611d61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80600b8381548110611d7557611d756135a7565b9060005260206000200154611d8a91906135d6565b3414611df2576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611e69576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80600003611ed3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56410000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611ede600e33612b35565b611eef57611eed600e33612b69565b505b600081600a8481548110611f0557611f056135a7565b600091825260208083209190910154338084526009835260409384902080549590920294850190915582513481529182018490529293507f3686dd4aa3f7c95dcac2734a95dcdcf29641e7e3f71f6ea1b39bc6bea5e36385910160405180910390a2505050565b60005473ffffffffffffffffffffffffffffffffffffffff163314611fed576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b805160005b818110156119db5761200f83828151811061193f5761193f6135a7565b1561204357612041838281518110612029576120296135a7565b60200260200101516006612c5090919063ffffffff16565b505b60006005600085848151811061205b5761205b6135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff16825281019190915260400160002055600101611ff2565b61209c612960565b60035415612106576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c54600003612172576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260056020526040902054156121e9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600082816122033360009081526008602052604090205490565b9050600061221d3360009081526009602052604090205490565b9050600061222b84876135d6565b905082156122425761223d8184613594565b612250565b80600d546122509190613594565b9250816000036122c8578234146122c3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61236b565b803414612331576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61236b33600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b6101f48411156123d7576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8794506123e5858588612c72565b604080518581526020810183905233917fca9fd6c3fcc68235a3c738db806875a8e98e0bcb25f11f56860971296c6de997910160405180910390a250505050506119db6001601055565b60005460609073ffffffffffffffffffffffffffffffffffffffff1633146124b3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6118976006612b21565b60005473ffffffffffffffffffffffffffffffffffffffff16331461253e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6002546040517f662aa11d00000000000000000000000000000000000000000000000000000000815230600482015273ffffffffffffffffffffffffffffffffffffffff90911660248201527343000000000000000000000000000000000000029063662aa11d906044016020604051808303816000875af11580156125c8573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906125ec91906135ed565b50565b60005473ffffffffffffffffffffffffffffffffffffffff163314612670576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600280547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b60005473ffffffffffffffffffffffffffffffffffffffff163381146126dc57600080fd5b600080600080476001545af16125ec57600080fd5b60005473ffffffffffffffffffffffffffffffffffffffff163314612772576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80518251146127dd576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b815160005b81811015612859578281815181106127fc576127fc6135a7565b60200260200101516009600086848151811061281a5761281a6135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff168252810191909152604001600020805490910190556001016127e2565b507f590a1a0c22d6042324e10baeee375e32704843a4630e1cc9889e30170a5a2efa838360405161288b929190613606565b60405180910390a1505050565b60005473ffffffffffffffffffffffffffffffffffffffff163314612919576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600180547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b60026010540361299c576040517f3ee5aeb500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6002601055565b6000805b838110156129de576020810283810135928301929086013590600080808084866108fcf16129d457600080fd5b50506001016129a7565b509392505050565b60405181606052306040523360601b602c526f23b872dd000000000000000000000000600c52602060006064601c60008a5af13d156001600051141716612a3557637939f4246000526004601cfd5b6000805b85811015612aa05760208181028681013560408190529089013560601b602c526fa9059cbb000000000000000000000000600c52929092019160006044601c828c5af13d156001600051141716612a9857637939f4246000526004601cfd5b600101612a39565b50808314612aad57600080fd5b5060006060526040525050505050565b60405160005b83811015612aad57602081028381013560609081529086013560405286901b602c526f23b872dd000000000000000000000000600c526000806064601c828b5af13d1516612b1957637939f4246000526004601cfd5b600101612ac3565b60606000612b2e83612ca2565b9392505050565b73ffffffffffffffffffffffffffffffffffffffff8116600090815260018301602052604081205415155b90505b92915050565b6000612b608373ffffffffffffffffffffffffffffffffffffffff8416612cfe565b81810260405181606052306040523360601b602c526f23b872dd000000000000000000000000600c52602060006064601c60008a5af13d156001600051141716612bdd57637939f4246000526004601cfd5b82604052600091505b83821015612c4157602082810286013560601b602c526fa9059cbb000000000000000000000000600c5260006044601c828a5af13d156001600051141716612c3657637939f4246000526004601cfd5b600182019150612be6565b60006060526040525050505050565b6000612b608373ffffffffffffffffffffffffffffffffffffffff8416612d4d565b60005b82811015611075576020810284013560008060008086856108fcf1612c9957600080fd5b50600101612c75565b606081600001805480602002602001604051908101604052809291908181526020018280548015612cf257602002820191906000526020600020905b815481526020019060010190808311612cde575b50505050509050919050565b6000818152600183016020526040812054612d4557508154600181810184556000848152602080822090930184905584548482528286019093526040902091909155612b63565b506000612b63565b60008181526001830160205260408120548015612e36576000612d71600183613619565b8554909150600090612d8590600190613619565b9050808214612dea576000866000018281548110612da557612da56135a7565b9060005260206000200154905080876000018481548110612dc857612dc86135a7565b6000918252602080832090910192909255918252600188019052604090208390555b8554869080612dfb57612dfb61362c565b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050612b63565b6000915050612b63565b828054828255906000526020600020908101928215612e7b579160200282015b82811115612e7b578251825591602001919060010190612e60565b50612e87929150612e8b565b5090565b5b80821115612e875760008155600101612e8c565b60008151808452602080850194506020840160005b83811015612ed157815187529582019590820190600101612eb5565b509495945050505050565b604081526000612eef6040830185612ea0565b8281036020840152612f018185612ea0565b95945050505050565b600060208284031215612f1c57600080fd5b5035919050565b803573ffffffffffffffffffffffffffffffffffffffff81168114612f4757600080fd5b919050565b60008060408385031215612f5f57600080fd5b612f6883612f23565b946020939093013593505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b604051601f82017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe016810167ffffffffffffffff81118282101715612fec57612fec612f76565b604052919050565b600067ffffffffffffffff82111561300e5761300e612f76565b5060051b60200190565b600082601f83011261302957600080fd5b8135602061303e61303983612ff4565b612fa5565b8083825260208201915060208460051b87010193508684111561306057600080fd5b602086015b8481101561307c5780358352918301918301613065565b509695505050505050565b6000806040838503121561309a57600080fd5b823567ffffffffffffffff808211156130b257600080fd5b6130be86838701613018565b935060208501359150808211156130d457600080fd5b506130e185828601613018565b9150509250929050565b60008060008060008060c0878903121561310457600080fd5b61310d87612f23565b955061311b60208801612f23565b945061312960408801612f23565b935060608701359250608087013567ffffffffffffffff8082111561314d57600080fd5b6131598a838b01613018565b935060a089013591508082111561316f57600080fd5b5061317c89828a01613018565b9150509295509295509295565b60008083601f84011261319b57600080fd5b50813567ffffffffffffffff8111156131b357600080fd5b6020830191508360208260051b85010111156131ce57600080fd5b9250929050565b600080600080604085870312156131eb57600080fd5b843567ffffffffffffffff8082111561320357600080fd5b61320f88838901613189565b9096509450602087013591508082111561322857600080fd5b5061323587828801613189565b95989497509550505050565b60006020828403121561325357600080fd5b612b6082612f23565b6000806000806000806080878903121561327557600080fd5b863567ffffffffffffffff8082111561328d57600080fd5b6132998a838b01613189565b909850965060208901359150808211156132b257600080fd5b506132bf89828a01613189565b90955093506132d2905060408801612f23565b9150606087013590509295509295509295565b6000806000806000606086880312156132fd57600080fd5b853567ffffffffffffffff8082111561331557600080fd5b61332189838a01613189565b9097509550602088013591508082111561333a57600080fd5b5061334788828901613189565b909450925061335a905060408701612f23565b90509295509295909350565b60008151808452602080850194506020840160005b83811015612ed157815173ffffffffffffffffffffffffffffffffffffffff168752958201959082019060010161337b565b602081526000612b606020830184613366565b600082601f8301126133d157600080fd5b813560206133e161303983612ff4565b8083825260208201915060208460051b87010193508684111561340357600080fd5b602086015b8481101561307c5761341981612f23565b8352918301918301613408565b60006020828403121561343857600080fd5b813567ffffffffffffffff81111561344f57600080fd5b61345b848285016133c0565b949350505050565b6000806000806060858703121561347957600080fd5b843567ffffffffffffffff81111561349057600080fd5b61349c87828801613189565b909550935050602085013591506134b560408601612f23565b905092959194509250565b600080604083850312156134d357600080fd5b50508035926020909101359150565b6000806000604084860312156134f757600080fd5b833567ffffffffffffffff81111561350e57600080fd5b61351a86828701613189565b909790965060209590950135949350505050565b6000806040838503121561354157600080fd5b823567ffffffffffffffff8082111561355957600080fd5b6130be868387016133c0565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b80820180821115612b6357612b63613565565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b8082028115828204841417612b6357612b63613565565b6000602082840312156135ff57600080fd5b5051919050565b604081526000612eef6040830185613366565b81810381811115612b6357612b63613565565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fdfea26469706673582212204bff4778ca8bc41e09be081e7bb135496707256ba4605a2f2b1a00c18da60f8f64736f6c63430008170033

Deployed Bytecode

0x6080604052600436106101c25760003560e01c80636ef25c3a116100f757806393f9e6f911610095578063d294f09311610064578063d294f09314610483578063d993cdff14610498578063e85ddb8a146104c5578063fe700990146104e557600080fd5b806393f9e6f914610423578063b2b8c93f14610438578063bd3b819f1461044d578063cddfa1a41461046d57600080fd5b80638634fd24116100d15780638634fd24146103ca57806388f941e8146103dd5780638a6ff456146103f05780638fc8b3b21461041057600080fd5b80636ef25c3a146103725780637850953d14610388578063798ed83d146103aa57600080fd5b806334ae8e3811610164578063586668061161013e578063586668061461031957806362274c2b1461032c5780636b55040f1461034c5780636c11d85a1461035f57600080fd5b806334ae8e38146102b757806347ec4ed1146102d7578063527d9730146102f957600080fd5b8063244bd967116101a0578063244bd96714610235578063286ddb681461025757806331fd0d7e1461027757806333f740a11461029757600080fd5b8063054f7d9c146101c757806320a225cb146101f057806322f10e2f14610213575b600080fd5b3480156101d357600080fd5b506101dd60035481565b6040519081526020015b60405180910390f35b3480156101fc57600080fd5b50610205610505565b6040516101e7929190612edc565b34801561021f57600080fd5b5061023361022e366004612f0a565b6105b2565b005b34801561024157600080fd5b50336000908152600960205260409020546101dd565b34801561026357600080fd5b50610233610272366004612f0a565b61063d565b34801561028357600080fd5b50610233610292366004612f0a565b6106c3565b3480156102a357600080fd5b506102336102b2366004612f4c565b610749565b3480156102c357600080fd5b506102336102d2366004613087565b61089b565b3480156102e357600080fd5b50336000908152600860205260409020546101dd565b34801561030557600080fd5b506102336103143660046130eb565b6109f7565b6102336103273660046131d5565b610cec565b34801561033857600080fd5b50610233610347366004613241565b61107b565b61023361035a36600461325c565b61114d565b61023361036d3660046132e5565b611471565b34801561037e57600080fd5b506101dd600d5481565b34801561039457600080fd5b5061039d611809565b6040516101e791906133ad565b3480156103b657600080fd5b506102336103c5366004613426565b61189c565b6102336103d8366004613463565b6119e0565b6102336103eb3660046134c0565b611cf7565b3480156103fc57600080fd5b5061023361040b366004613426565b611f6c565b61023361041e3660046134e2565b612094565b34801561042f57600080fd5b5061039d61242f565b34801561044457600080fd5b506102336124bd565b34801561045957600080fd5b50610233610468366004613241565b6125ef565b34801561047957600080fd5b506101dd60045481565b34801561048f57600080fd5b506102336126b7565b3480156104a457600080fd5b506101dd6104b3366004613241565b60096020526000908152604090205481565b3480156104d157600080fd5b506102336104e036600461352e565b6126f1565b3480156104f157600080fd5b50610233610500366004613241565b612898565b606080600a80548060200260200160405190810160405280929190818152602001828054801561055457602002820191906000526020600020905b815481526020019060010190808311610540575b50505050509150600b8054806020026020016040519081016040528092919081815260200182805480156105a757602002820191906000526020600020905b815481526020019060010190808311610593575b505050505090509091565b60005473ffffffffffffffffffffffffffffffffffffffff163314610638576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e5653000000000000000000000000000000000000000000000000000000000060448201526064015b60405180910390fd5b600d55565b60005473ffffffffffffffffffffffffffffffffffffffff1633146106be576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600355565b60005473ffffffffffffffffffffffffffffffffffffffff163314610744576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600455565b600d5481106107b4576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b60005473ffffffffffffffffffffffffffffffffffffffff163314610835576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b73ffffffffffffffffffffffffffffffffffffffff821660008181526008602052604090819020839055517f44784c405393a593553ed0bf0ddb15aa2494ba9b97a8d75dfc9fabb7a64c8ce59061088f9084815260200190565b60405180910390a25050565b60005473ffffffffffffffffffffffffffffffffffffffff16331461091c576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8051825114610987576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56440000000000000000000000000000000000000000000000000000000000604482015260640161062f565b815161099a90600a906020850190612e40565b5080516109ae90600b906020840190612e40565b503373ffffffffffffffffffffffffffffffffffffffff167fed68a7a2289c86234d260dc96066680ff0bcde7d3376a219df515dde860435b1838360405161088f929190612edc565b600c5415610a61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4149000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8051825114610acc576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56440000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6000805473ffffffffffffffffffffffffffffffffffffffff8089167fffffffffffffffffffffffff0000000000000000000000000000000000000000928316179092556001805488841690831617905560028054928716929091169190911790558151610b4190600a906020850190612e40565b508051610b5590600b906020840190612e40565b506001600c55600d839055604080517f7114177a000000000000000000000000000000000000000000000000000000008152905173430000000000000000000000000000000000000291637114177a91600480830192600092919082900301818387803b158015610bc557600080fd5b505af1158015610bd9573d6000803e3d6000fd5b5050505073430000000000000000000000000000000000000273ffffffffffffffffffffffffffffffffffffffff16634e606c476040518163ffffffff1660e01b8152600401600060405180830381600087803b158015610c3957600080fd5b505af1158015610c4d573d6000803e3d6000fd5b50506040517f36b91f2b00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff89166004820152732536fe9ab3f511540f2f9e2ec2a805005c3dd80092506336b91f2b9150602401600060405180830381600087803b158015610ccc57600080fd5b505af1158015610ce0573d6000803e3d6000fd5b50505050505050505050565b610cf4612960565b60035415610d5e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c54600003610dca576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415610e41576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b336000908152600860209081526040808320546009909252822054909180866101f48111801590610e7157508086145b610ed7576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8892508691506000610eea8483856129a3565b90508515610f0157610efc8187613594565b610f0f565b80600d54610f0f9190613594565b955084600003610f8757853414610f82576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61102a565b803414610ff0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61102a33600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b604080518381526020810183905233917f2c7cd2d52efdb7bcb324ce1fdaad584211503edbbf94fa7a3fde2624da572642910160405180910390a25050505050506110756001601055565b50505050565b60005473ffffffffffffffffffffffffffffffffffffffff1633146110fc576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b73ffffffffffffffffffffffffffffffffffffffff8116600081815260086020526040808220829055517f9a93cb5054fe47b6e8ec0e29a26edd6249309d823eccab337b5c81dda65f6ddc9190a250565b611155612960565b600354156111bf576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611236576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526008602090815260408083205460099092529091205486821561125f5782611263565b600d545b9250816000036112db578234146112d6576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611315565b61131533600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b600c54600003611381576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6101f4811115801561139257508086145b6113f8576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8887611407878385848a6129e6565b604080518481526020810188905273ffffffffffffffffffffffffffffffffffffffff89169133917f0e18fd6025578556afc2d4c83f1e98be2ddb206457774fa37a3a8b1605ad6f79910160405180910390a350505050506114696001601055565b505050505050565b611479612960565b6004546000036114e5576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e45590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6003541561154f576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c546000036115bb576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611632576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260086020526040902054801561164e5780611652565b600d545b9050600061166c3360009081526009602052604090205490565b90508560008290036116e6578234146116e1576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611720565b61172033600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b6101f4811115801561173157508085145b611797576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b87866117a68633848685612abd565b60405183815273ffffffffffffffffffffffffffffffffffffffff87169033907f4bd386a75bd69ced877c29ffb9d2058eeed770d425c9027116b45e6f0fb4645a9060200160405180910390a350505050506118026001601055565b5050505050565b60005460609073ffffffffffffffffffffffffffffffffffffffff16331461188d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611897600e612b21565b905090565b60005473ffffffffffffffffffffffffffffffffffffffff16331461191d576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b805160005b818110156119db5761195783828151811061193f5761193f6135a7565b60200260200101516006612b3590919063ffffffff16565b61198a57611988838281518110611970576119706135a7565b60200260200101516006612b6990919063ffffffff16565b505b6001600560008584815181106119a2576119a26135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff16825281019190915260400160002055600101611922565b505050565b6119e8612960565b60035415611a52576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611ac9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260086020908152604080832054600990925290912054848215611af25782611af6565b600d545b925081600003611b6e57823414611b69576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611ba8565b611ba833600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b600c54600003611c14576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6101f4811115611c80576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b86611c8d85828489612b8b565b73ffffffffffffffffffffffffffffffffffffffff8516337fbfc5bd893849e5d9bf1ac87d7e1fcec4f9afece75f87062d0c2370f1c6b5734b84611cd18a826135d6565b6040805192835260208301919091520160405180910390a3505050506110756001601055565b60035415611d61576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80600b8381548110611d7557611d756135a7565b9060005260206000200154611d8a91906135d6565b3414611df2576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b3360009081526005602052604090205415611e69576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80600003611ed3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56410000000000000000000000000000000000000000000000000000000000604482015260640161062f565b611ede600e33612b35565b611eef57611eed600e33612b69565b505b600081600a8481548110611f0557611f056135a7565b600091825260208083209190910154338084526009835260409384902080549590920294850190915582513481529182018490529293507f3686dd4aa3f7c95dcac2734a95dcdcf29641e7e3f71f6ea1b39bc6bea5e36385910160405180910390a2505050565b60005473ffffffffffffffffffffffffffffffffffffffff163314611fed576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b805160005b818110156119db5761200f83828151811061193f5761193f6135a7565b1561204357612041838281518110612029576120296135a7565b60200260200101516006612c5090919063ffffffff16565b505b60006005600085848151811061205b5761205b6135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff16825281019190915260400160002055600101611ff2565b61209c612960565b60035415612106576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f4346000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600c54600003612172576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e49590000000000000000000000000000000000000000000000000000000000604482015260640161062f565b33600090815260056020526040902054156121e9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600260248201527f5544000000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600082816122033360009081526008602052604090205490565b9050600061221d3360009081526009602052604090205490565b9050600061222b84876135d6565b905082156122425761223d8184613594565b612250565b80600d546122509190613594565b9250816000036122c8578234146122c3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61236b565b803414612331576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56560000000000000000000000000000000000000000000000000000000000604482015260640161062f565b61236b33600090815260096020526040902080547fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff019055565b6101f48411156123d7576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b8794506123e5858588612c72565b604080518581526020810183905233917fca9fd6c3fcc68235a3c738db806875a8e98e0bcb25f11f56860971296c6de997910160405180910390a250505050506119db6001601055565b60005460609073ffffffffffffffffffffffffffffffffffffffff1633146124b3576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6118976006612b21565b60005473ffffffffffffffffffffffffffffffffffffffff16331461253e576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b6002546040517f662aa11d00000000000000000000000000000000000000000000000000000000815230600482015273ffffffffffffffffffffffffffffffffffffffff90911660248201527343000000000000000000000000000000000000029063662aa11d906044016020604051808303816000875af11580156125c8573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906125ec91906135ed565b50565b60005473ffffffffffffffffffffffffffffffffffffffff163314612670576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600280547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b60005473ffffffffffffffffffffffffffffffffffffffff163381146126dc57600080fd5b600080600080476001545af16125ec57600080fd5b60005473ffffffffffffffffffffffffffffffffffffffff163314612772576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b80518251146127dd576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e564c0000000000000000000000000000000000000000000000000000000000604482015260640161062f565b815160005b81811015612859578281815181106127fc576127fc6135a7565b60200260200101516009600086848151811061281a5761281a6135a7565b60209081029190910181015173ffffffffffffffffffffffffffffffffffffffff168252810191909152604001600020805490910190556001016127e2565b507f590a1a0c22d6042324e10baeee375e32704843a4630e1cc9889e30170a5a2efa838360405161288b929190613606565b60405180910390a1505050565b60005473ffffffffffffffffffffffffffffffffffffffff163314612919576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600360248201527f4e56530000000000000000000000000000000000000000000000000000000000604482015260640161062f565b600180547fffffffffffffffffffffffff00000000000000000000000000000000000000001673ffffffffffffffffffffffffffffffffffffffff92909216919091179055565b60026010540361299c576040517f3ee5aeb500000000000000000000000000000000000000000000000000000000815260040160405180910390fd5b6002601055565b6000805b838110156129de576020810283810135928301929086013590600080808084866108fcf16129d457600080fd5b50506001016129a7565b509392505050565b60405181606052306040523360601b602c526f23b872dd000000000000000000000000600c52602060006064601c60008a5af13d156001600051141716612a3557637939f4246000526004601cfd5b6000805b85811015612aa05760208181028681013560408190529089013560601b602c526fa9059cbb000000000000000000000000600c52929092019160006044601c828c5af13d156001600051141716612a9857637939f4246000526004601cfd5b600101612a39565b50808314612aad57600080fd5b5060006060526040525050505050565b60405160005b83811015612aad57602081028381013560609081529086013560405286901b602c526f23b872dd000000000000000000000000600c526000806064601c828b5af13d1516612b1957637939f4246000526004601cfd5b600101612ac3565b60606000612b2e83612ca2565b9392505050565b73ffffffffffffffffffffffffffffffffffffffff8116600090815260018301602052604081205415155b90505b92915050565b6000612b608373ffffffffffffffffffffffffffffffffffffffff8416612cfe565b81810260405181606052306040523360601b602c526f23b872dd000000000000000000000000600c52602060006064601c60008a5af13d156001600051141716612bdd57637939f4246000526004601cfd5b82604052600091505b83821015612c4157602082810286013560601b602c526fa9059cbb000000000000000000000000600c5260006044601c828a5af13d156001600051141716612c3657637939f4246000526004601cfd5b600182019150612be6565b60006060526040525050505050565b6000612b608373ffffffffffffffffffffffffffffffffffffffff8416612d4d565b60005b82811015611075576020810284013560008060008086856108fcf1612c9957600080fd5b50600101612c75565b606081600001805480602002602001604051908101604052809291908181526020018280548015612cf257602002820191906000526020600020905b815481526020019060010190808311612cde575b50505050509050919050565b6000818152600183016020526040812054612d4557508154600181810184556000848152602080822090930184905584548482528286019093526040902091909155612b63565b506000612b63565b60008181526001830160205260408120548015612e36576000612d71600183613619565b8554909150600090612d8590600190613619565b9050808214612dea576000866000018281548110612da557612da56135a7565b9060005260206000200154905080876000018481548110612dc857612dc86135a7565b6000918252602080832090910192909255918252600188019052604090208390555b8554869080612dfb57612dfb61362c565b600190038181906000526020600020016000905590558560010160008681526020019081526020016000206000905560019350505050612b63565b6000915050612b63565b828054828255906000526020600020908101928215612e7b579160200282015b82811115612e7b578251825591602001919060010190612e60565b50612e87929150612e8b565b5090565b5b80821115612e875760008155600101612e8c565b60008151808452602080850194506020840160005b83811015612ed157815187529582019590820190600101612eb5565b509495945050505050565b604081526000612eef6040830185612ea0565b8281036020840152612f018185612ea0565b95945050505050565b600060208284031215612f1c57600080fd5b5035919050565b803573ffffffffffffffffffffffffffffffffffffffff81168114612f4757600080fd5b919050565b60008060408385031215612f5f57600080fd5b612f6883612f23565b946020939093013593505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b604051601f82017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe016810167ffffffffffffffff81118282101715612fec57612fec612f76565b604052919050565b600067ffffffffffffffff82111561300e5761300e612f76565b5060051b60200190565b600082601f83011261302957600080fd5b8135602061303e61303983612ff4565b612fa5565b8083825260208201915060208460051b87010193508684111561306057600080fd5b602086015b8481101561307c5780358352918301918301613065565b509695505050505050565b6000806040838503121561309a57600080fd5b823567ffffffffffffffff808211156130b257600080fd5b6130be86838701613018565b935060208501359150808211156130d457600080fd5b506130e185828601613018565b9150509250929050565b60008060008060008060c0878903121561310457600080fd5b61310d87612f23565b955061311b60208801612f23565b945061312960408801612f23565b935060608701359250608087013567ffffffffffffffff8082111561314d57600080fd5b6131598a838b01613018565b935060a089013591508082111561316f57600080fd5b5061317c89828a01613018565b9150509295509295509295565b60008083601f84011261319b57600080fd5b50813567ffffffffffffffff8111156131b357600080fd5b6020830191508360208260051b85010111156131ce57600080fd5b9250929050565b600080600080604085870312156131eb57600080fd5b843567ffffffffffffffff8082111561320357600080fd5b61320f88838901613189565b9096509450602087013591508082111561322857600080fd5b5061323587828801613189565b95989497509550505050565b60006020828403121561325357600080fd5b612b6082612f23565b6000806000806000806080878903121561327557600080fd5b863567ffffffffffffffff8082111561328d57600080fd5b6132998a838b01613189565b909850965060208901359150808211156132b257600080fd5b506132bf89828a01613189565b90955093506132d2905060408801612f23565b9150606087013590509295509295509295565b6000806000806000606086880312156132fd57600080fd5b853567ffffffffffffffff8082111561331557600080fd5b61332189838a01613189565b9097509550602088013591508082111561333a57600080fd5b5061334788828901613189565b909450925061335a905060408701612f23565b90509295509295909350565b60008151808452602080850194506020840160005b83811015612ed157815173ffffffffffffffffffffffffffffffffffffffff168752958201959082019060010161337b565b602081526000612b606020830184613366565b600082601f8301126133d157600080fd5b813560206133e161303983612ff4565b8083825260208201915060208460051b87010193508684111561340357600080fd5b602086015b8481101561307c5761341981612f23565b8352918301918301613408565b60006020828403121561343857600080fd5b813567ffffffffffffffff81111561344f57600080fd5b61345b848285016133c0565b949350505050565b6000806000806060858703121561347957600080fd5b843567ffffffffffffffff81111561349057600080fd5b61349c87828801613189565b909550935050602085013591506134b560408601612f23565b905092959194509250565b600080604083850312156134d357600080fd5b50508035926020909101359150565b6000806000604084860312156134f757600080fd5b833567ffffffffffffffff81111561350e57600080fd5b61351a86828701613189565b909790965060209590950135949350505050565b6000806040838503121561354157600080fd5b823567ffffffffffffffff8082111561355957600080fd5b6130be868387016133c0565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b80820180821115612b6357612b63613565565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b8082028115828204841417612b6357612b63613565565b6000602082840312156135ff57600080fd5b5051919050565b604081526000612eef6040830185613366565b81810381811115612b6357612b63613565565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603160045260246000fdfea26469706673582212204bff4778ca8bc41e09be081e7bb135496707256ba4605a2f2b1a00c18da60f8f64736f6c63430008170033

Block Transaction Difficulty Gas Used Reward
View All Blocks Produced

Block Uncle Number Difficulty Gas Used Reward
View All Uncles
Loading...
Loading

OVERVIEW

SlashToken provides user-friendly token and NFT tools to help Web3 projects to better engage and reward their communities. SlashToken Drop is a fast and budget-friendly way to send tokens and NFTs to multiple wallets - in just a few clicks.

Loading...
Loading

Validator Index Block Amount
View All Withdrawals

Transaction Hash Block Value Eth2 PubKey Valid
View All Deposits
[ Download: CSV Export  ]
[ Download: CSV Export  ]

A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.