// Contract: VokenPublicSale2
// Target function: function rescueTokens(address tokenAddr, address recipient, uint256 amount) external onlyOwner
pragma solidity ^0.5.11;

    // Public-Sale for #3277-12000 stage of Voken2.0
    //
    // More info:
    //   https://vision.network
    //   https://voken.io
    //
    // Contact us:
    //   support@vision.network
    //   support@voken.io


    /**
     * @dev Uint256 wrappers over Solidity's arithmetic operations with added overflow checks.
     */
    library SafeMath256 {
        /**
         * @dev Returns the addition of two unsigned integers, reverting on overflow.
         */
        function add(uint256 a, uint256 b) internal pure returns (uint256) {
            uint256 c = a + b;
            require(c >= a, "SafeMath: addition overflow");

            return c;
        }

        /**
         * @dev Returns the subtraction of two unsigned integers, reverting on
         * overflow (when the result is negative).
         */
        function sub(uint256 a, uint256 b) internal pure returns (uint256) {
            return sub(a, b, "SafeMath: subtraction overflow");
        }

        /**
         * @dev Returns the subtraction of two unsigned integers, reverting with custom message on
         * overflow (when the result is negative).
         */
        function sub(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
            require(b <= a, errorMessage);
            uint256 c = a - b;

            return c;
        }

        /**
         * @dev Returns the multiplication of two unsigned integers, reverting on overflow.
         */
        function mul(uint256 a, uint256 b) internal pure returns (uint256) {
            if (a == 0) {
                return 0;
            }

            uint256 c = a * b;
            require(c / a == b, "SafeMath: multiplication overflow");

            return c;
        }

        /**
         * @dev Returns the integer division of two unsigned integers. Reverts on
         * division by zero. The result is rounded towards zero.
         */
        function div(uint256 a, uint256 b) internal pure returns (uint256) {
            return div(a, b, "SafeMath: division by zero");
        }

        /**
         * @dev Returns the integer division of two unsigned integers. Reverts with custom message on
         * division by zero. The result is rounded towards zero.
         */
        function div(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
            // Solidity only automatically asserts when dividing by 0
            require(b > 0, errorMessage);
            return a / b;
        }

        /**
         * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
         * Reverts when dividing by zero.
         */
        function mod(uint256 a, uint256 b) internal pure returns (uint256) {
            return mod(a, b, "SafeMath: modulo by zero");
        }

        /**
         * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
         * Reverts with custom message when dividing by zero.
         */
        function mod(uint256 a, uint256 b, string memory errorMessage) internal pure returns (uint256) {
            require(b != 0, errorMessage);
            return a % b;
        }
    }


    /**
     * @dev Uint16 wrappers over Solidity's arithmetic operations with added overflow checks.
     */
    library SafeMath16 {
        /**
         * @dev Returns the addition of two unsigned integers, reverting on overflow.
         */
        function add(uint16 a, uint16 b) internal pure returns (uint16) {
            uint16 c = a + b;
            require(c >= a, "SafeMath: addition overflow");

            return c;
        }

        /**
         * @dev Returns the subtraction of two unsigned integers, reverting on
         * overflow (when the result is negative).
         */
        function sub(uint16 a, uint16 b) internal pure returns (uint16) {
            return sub(a, b, "SafeMath: subtraction overflow");
        }

        /**
         * @dev Returns the subtraction of two unsigned integers, reverting with custom message on
         * overflow (when the result is negative).
         */
        function sub(uint16 a, uint16 b, string memory errorMessage) internal pure returns (uint16) {
            require(b <= a, errorMessage);
            uint16 c = a - b;

            return c;
        }

        /**
         * @dev Returns the multiplication of two unsigned integers, reverting on overflow.
         */
        function mul(uint16 a, uint16 b) internal pure returns (uint16) {
            if (a == 0) {
                return 0;
            }

            uint16 c = a * b;
            require(c / a == b, "SafeMath: multiplication overflow");

            return c;
        }

        /**
         * @dev Returns the integer division of two unsigned integers. Reverts on
         * division by zero. The result is rounded towards zero.
         */
        function div(uint16 a, uint16 b) internal pure returns (uint16) {
            return div(a, b, "SafeMath: division by zero");
        }

        /**
         * @dev Returns the integer division of two unsigned integers. Reverts with custom message on
         * division by zero. The result is rounded towards zero.
         */
        function div(uint16 a, uint16 b, string memory errorMessage) internal pure returns (uint16) {
            // Solidity only automatically asserts when dividing by 0
            require(b > 0, errorMessage);
            return a / b;
        }

        /**
         * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
         * Reverts when dividing by zero.
         */
        function mod(uint16 a, uint16 b) internal pure returns (uint16) {
            return mod(a, b, "SafeMath: modulo by zero");
        }

        /**
         * @dev Returns the remainder of dividing two unsigned integers. (unsigned integer modulo),
         * Reverts with custom message when dividing by zero.
         */
        function mod(uint16 a, uint16 b, string memory errorMessage) internal pure returns (uint16) {
            require(b != 0, errorMessage);
            return a % b;
        }
    }


    /**
     * @title Roles
     * @dev Library for managing addresses assigned to a Role.
     */
    library Roles {
        struct Role {
            mapping (address => bool) bearer;
        }

        /**
         * @dev Give an account access to this role.
         */
        function add(Role storage role, address account) internal {
            require(!has(role, account), "Roles: account already has role");
            role.bearer[account] = true;
        }

        /**
         * @dev Remove an account's access to this role.
         */
        function remove(Role storage role, address account) internal {
            require(has(role, account), "Roles: account does not have role");
            role.bearer[account] = false;
        }

        /**
         * @dev Check if an account has this role.
         * @return bool
         */
        function has(Role storage role, address account) internal view returns (bool) {
            require(account != address(0), "Roles: account is the zero address");
            return role.bearer[account];
        }
    }

    /**
     * @dev Contract module which provides a basic access control mechanism, where
     * there is an account (an owner) that can be granted exclusive access to
     * specific functions.
     */
    contract Ownable {
        address internal _owner;
        address internal _newOwner;

        event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
        event OwnershipAccepted(address indexed previousOwner, address indexed newOwner);


        /**
         * @dev Initializes the contract setting the deployer as the initial owner.
         */
        constructor () internal {
            _owner = msg.sender;
            emit OwnershipTransferred(address(0), _owner);
        }

        /**
         * @dev Returns the addresses of the current and new owner.
         */
        function owner() public view returns (address currentOwner, address newOwner) {
            currentOwner = _owner;
            newOwner = _newOwner;
        }

        /**
         * @dev Throws if called by any account other than the owner.
         */
        modifier onlyOwner() {
            require(isOwner(msg.sender), "Ownable: caller is not the owner");
            _;
        }

        /**
         * @dev Returns true if the caller is the current owner.
         */
        function isOwner(address account) public view returns (bool) {
            return account == _owner;
        }

        /**
         * @dev Transfers ownership of the contract to a new account (`newOwner`).
         *
         * IMPORTANT: Need to run {acceptOwnership} by the new owner.
         */
        function _transferOwnership(address newOwner) internal {
            require(newOwner != address(0), "Ownable: new owner is the zero address");

            emit OwnershipTransferred(_owner, newOwner);
            _newOwner = newOwner;
        }

        /**
         * @dev Transfers ownership of the contract to a new account (`newOwner`).
         *
         * Can only be called by the current owner.
         */
        function transferOwnership(address newOwner) public onlyOwner {
            _transferOwnership(newOwner);
        }

        /**
         * @dev Accept ownership of the contract.
         *
         * Can only be called by the new owner.
         */
        function acceptOwnership() public {
            require(msg.sender == _newOwner, "Ownable: caller is not the new owner address");
            require(msg.sender != address(0), "Ownable: caller is the zero address");

            emit OwnershipAccepted(_owner, msg.sender);
            _owner = msg.sender;
            _newOwner = address(0);
        }