Forkchoice Ethereum Mainnet

Address Contract Partially Verified

Address 0xE59dbF08CccF8D1ab90156b9664d31Fd20BB2AC7
Balance 0 ETH
Nonce 1
Code Size 1527 bytes
Indexed Transactions 0 (1 on-chain, 0.7% indexed)
External Etherscan · Sourcify

Contract Bytecode

1527 bytes
0x608060405234801561001057600080fd5b50600436106100885760003560e01c80638da5cb5b1161005b5780638da5cb5b146100ce578063e30c3978146100f3578063e8c7e72814610104578063f2fde38b1461010c57600080fd5b80635b2ec32b1461008d5780636c7c1cbb146100a2578063715018a6146100be57806379ba5097146100c6575b600080fd5b6100a061009b366004610429565b61011f565b005b6100ab60025481565b6040519081526020015b60405180910390f35b6100a061019c565b6100a06101d2565b6000546001600160a01b03165b6040516001600160a01b0390911681526020016100b5565b6001546001600160a01b03166100db565b6100a061024c565b6100a061011a366004610442565b6102ae565b6000546001600160a01b031633146101525760405162461bcd60e51b81526004016101499061046b565b60405180910390fd5b61015b81610391565b60025460408051918252602082018390527fabb7cb8904df4b6cf0918b8b3ba9ccc27f9750eaf04f9a78507ead12babdabc8910160405180910390a1600255565b6000546001600160a01b031633146101c65760405162461bcd60e51b81526004016101499061046b565b6101d060006103d5565b565b60015433906001600160a01b031681146102405760405162461bcd60e51b815260206004820152602960248201527f4f776e61626c6532537465703a2063616c6c6572206973206e6f7420746865206044820152683732bb9037bbb732b960b91b6064820152608401610149565b610249816103d5565b50565b600080600254121561027557600254610264906104b6565b61026e90426104d2565b9050610285565b60025461028290426104eb565b90505b6006610290826103ee565b106102495760405163374b0d0760e11b815260040160405180910390fd5b6000546001600160a01b031633146102d85760405162461bcd60e51b81526004016101499061046b565b600180546001600160a01b0383166001600160a01b031990911681179091556103096000546001600160a01b031690565b6001600160a01b03167f38d16b8cac22d99fc7c124b9cd0de2d3fa1faef420bfe791d8c362d765e2270060405160405180910390a350565b600080546001600160a01b038381166001600160a01b0319831681178455604051919092169283917f8be0079c531659141344cd1fd0a4f28419497f9722a3daafe3b4186f6b6457e09190a35050565b61039f610e10600b196104fe565b8112806103b757506103b4610e10600e6104fe565b81135b156102495760405163025d6fbf60e41b815260040160405180910390fd5b600180546001600160a01b031916905561024981610341565b6000806103fe6201518084610599565b9050600761040d8260036104eb565b61041791906105ad565b6104229060016104eb565b9392505050565b60006020828403121561043b57600080fd5b5035919050565b60006020828403121561045457600080fd5b81356001600160a01b038116811461042257600080fd5b6020808252818101527f4f776e61626c653a2063616c6c6572206973206e6f7420746865206f776e6572604082015260600190565b634e487b7160e01b600052601160045260246000fd5b6000600160ff1b82016104cb576104cb6104a0565b5060000390565b818103818111156104e5576104e56104a0565b92915050565b808201808211156104e5576104e56104a0565b60006001600160ff1b0381841382841380821686840486111615610524576105246104a0565b600160ff1b6000871282811687830589121615610543576105436104a0565b6000871292508782058712848416161561055f5761055f6104a0565b87850587128184161615610575576105756104a0565b505050929093029392505050565b634e487b7160e01b600052601260045260246000fd5b6000826105a8576105a8610583565b500490565b6000826105bc576105bc610583565b50069056fea2646970667358221220307824cae27e6ba53caf59f820126c8ba0191c74177a7bee6afe43ca5cc9e9de64736f6c63430008100033

Verified Source Code Partial Match

Compiler: v0.8.16+commit.07a7930e EVM: london Optimization: Yes (200 runs)
IssuanceHours.sol 112 lines
/**SPDX-License-Identifier: BUSL-1.1

      ▄▄█████████▄
   ╓██▀└ ,╓▄▄▄, '▀██▄
  ██▀ ▄██▀▀╙╙▀▀██▄ └██µ           ,,       ,,      ,     ,,,            ,,,
 ██ ,██¬ ▄████▄  ▀█▄ ╙█▄      ▄███▀▀███▄   ███▄    ██  ███▀▀▀███▄    ▄███▀▀███,
██  ██ ╒█▀'   ╙█▌ ╙█▌ ██     ▐██      ███  █████,  ██  ██▌    └██▌  ██▌     └██▌
██ ▐█▌ ██      ╟█  █▌ ╟█     ██▌      ▐██  ██ └███ ██  ██▌     ╟██ j██       ╟██
╟█  ██ ╙██    ▄█▀ ▐█▌ ██     ╙██      ██▌  ██   ╙████  ██▌    ▄██▀  ██▌     ,██▀
 ██ "██, ╙▀▀███████████⌐      ╙████████▀   ██     ╙██  ███████▀▀     ╙███████▀`
  ██▄ ╙▀██▄▄▄▄▄,,,                ¬─                                    '─¬
   ╙▀██▄ '╙╙╙▀▀▀▀▀▀▀▀
      ╙▀▀██████R⌐

 */
pragma solidity 0.8.16;
import "contracts/globalMarkets/tokenManager/issuanceHours/IIssuanceHours.sol";
import "contracts/external/openzeppelin/contracts/access/Ownable2Step.sol";
import "contracts/external/openzeppelin/contracts/access/Ownable.sol";
import "contracts/external/BokkyPooBahsDateTimeLibrary/BokkyPooBahsDateTimeLibrary.sol";

/**
 * @title  IssuanceHours
 * @author Ondo Finance
 * @notice This contract is used to check if the current time is within the
 *         issuance hours for a given market. The issuance hours are defined
 *         as Monday to Friday 24/5.
 *
 * @dev    This is a naive layer of protection for defense-in-depth, and should not be
 *         relied upon for any critical functionality. It is intended to be used as
 *         a fail safe for the quoting engine signing invalid attestations.
 */
contract IssuanceHours is IIssuanceHours, Ownable2Step {
  /// The timezone offset in seconds from UTC. Can be negative (west of UTC) or positive (east of UTC)
  int256 public timezoneOffset;

  /// Constant for the number of seconds in an hour
  int256 constant HOUR_IN_SECONDS = 3_600;

  /**
   * @notice Event emitted when the timezone offset is set
   * @param  prevTimezoneOffset The previous timezone offset in seconds from UTC
   * @param  newTimezoneOffset  The new timezone offset in seconds from UTC
   */
  event SetTimezoneOffset(int256 prevTimezoneOffset, int256 newTimezoneOffset);

  /// Error emitted when the current time is not within the issuance hours
  error OutsideMarketHours();

  /// Error emitted when the timezone offset exceeds the maximum allowed value
  error MaximumOffsetExceeded();

  /**
   * @notice Constructor for the MarketIssuanceHours contract
   * @param  admin           The address of the admin for the contract
   * @param  _timezoneOffset The timezone offset in seconds from UTC
   * @dev    The timezone offset is used to determine the issuance hours for
   *         the market.
   */
  constructor(address admin, int256 _timezoneOffset) {
    _validateTimezoneOffset(_timezoneOffset);

    timezoneOffset = _timezoneOffset;

    _transferOwnership(admin);
  }

  /**
   * @notice Check if the current time is within the market hours
   * @dev    The function computes the day of the week based on the current block timestamp
   *         and checks if it is within the issuance hours. This does ignore holidays as it
   *         is only intended to be a fail safe for the quoting engine signing invalid attestations.
   */
  function checkIsValidHours() external view {
    uint256 adjustedTimestamp;
    if (timezoneOffset < 0) {
      adjustedTimestamp = block.timestamp - uint256(-timezoneOffset);
    } else {
      adjustedTimestamp = block.timestamp + uint256(timezoneOffset);
    }

    if (BokkyPooBahsDateTimeLibrary.getDayOfWeek(adjustedTimestamp) >= 6) {
      revert OutsideMarketHours();
    }
  }

  /**
   * @notice Set the timezone offset in seconds from UTC
   * @param  _timezoneOffset The new timezone offset in seconds from UTC
   * @dev    This function can only be called by the owner of the contract
   */
  function setTimezoneOffset(int256 _timezoneOffset) public onlyOwner {
    _validateTimezoneOffset(_timezoneOffset);

    emit SetTimezoneOffset(timezoneOffset, _timezoneOffset);

    timezoneOffset = _timezoneOffset;
  }

  /**
   * @notice Validate the timezone offset
   * @param  _timezoneOffset The timezone offset in seconds from UTC
   * @dev    This function checks if the timezone offset is within the allowed range
   *         of -12 to +14 hours. If it is not, it reverts with MaximumOffsetExceeded error.
   */
  function _validateTimezoneOffset(int256 _timezoneOffset) private pure {
    if (
      _timezoneOffset < -12 * HOUR_IN_SECONDS ||
      _timezoneOffset > 14 * HOUR_IN_SECONDS
    ) revert MaximumOffsetExceeded();
  }
}
IIssuanceHours.sol 24 lines
// SPDX-License-Identifier: BUSL-1.1
/*
      ▄▄█████████▄
   ╓██▀└ ,╓▄▄▄, '▀██▄
  ██▀ ▄██▀▀╙╙▀▀██▄ └██µ           ,,       ,,      ,     ,,,            ,,,
 ██ ,██¬ ▄████▄  ▀█▄ ╙█▄      ▄███▀▀███▄   ███▄    ██  ███▀▀▀███▄    ▄███▀▀███,
██  ██ ╒█▀'   ╙█▌ ╙█▌ ██     ▐██      ███  █████,  ██  ██▌    └██▌  ██▌     └██▌
██ ▐█▌ ██      ╟█  █▌ ╟█     ██▌      ▐██  ██ └███ ██  ██▌     ╟██ j██       ╟██
╟█  ██ ╙██    ▄█▀ ▐█▌ ██     ╙██      ██▌  ██   ╙████  ██▌    ▄██▀  ██▌     ,██▀
 ██ "██, ╙▀▀███████████⌐      ╙████████▀   ██     ╙██  ███████▀▀     ╙███████▀`
  ██▄ ╙▀██▄▄▄▄▄,,,                ¬─                                    '─¬
   ╙▀██▄ '╙╙╙▀▀▀▀▀▀▀▀
      ╙▀▀██████R⌐
 */
pragma solidity 0.8.16;

/**
 * @title  IIssuanceHours
 * @author Ondo Finance
 * @notice Interface for checking if current time is within valid market hours
 */
interface IIssuanceHours {
  function checkIsValidHours() external;
}
Ownable2Step.sol 57 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts (last updated v4.8.0) (access/Ownable2Step.sol)

pragma solidity ^0.8.0;

import "./Ownable.sol";

/**
 * @dev Contract module which provides access control mechanism, where
 * there is an account (an owner) that can be granted exclusive access to
 * specific functions.
 *
 * By default, the owner account will be the one that deploys the contract. This
 * can later be changed with {transferOwnership} and {acceptOwnership}.
 *
 * This module is used through inheritance. It will make available all functions
 * from parent (Ownable).
 */
abstract contract Ownable2Step is Ownable {
    address private _pendingOwner;

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

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

    /**
     * @dev Starts the ownership transfer of the contract to a new account. Replaces the pending transfer if there is one.
     * Can only be called by the current owner.
     */
    function transferOwnership(address newOwner) public virtual override onlyOwner {
        _pendingOwner = newOwner;
        emit OwnershipTransferStarted(owner(), newOwner);
    }

    /**
     * @dev Transfers ownership of the contract to a new account (`newOwner`) and deletes any pending owner.
     * Internal function without access restriction.
     */
    function _transferOwnership(address newOwner) internal virtual override {
        delete _pendingOwner;
        super._transferOwnership(newOwner);
    }

    /**
     * @dev The new owner accepts the ownership transfer.
     */
    function acceptOwnership() public virtual {
        address sender = _msgSender();
        require(pendingOwner() == sender, "Ownable2Step: caller is not the new owner");
        _transferOwnership(sender);
    }
}
Ownable.sol 79 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (access/Ownable.sol)

pragma solidity ^0.8.0;

import "contracts/external/openzeppelin/contracts/utils/Context.sol";

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

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

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

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

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

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

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

  /**
   * @dev Transfers ownership of the contract to a new account (`newOwner`).
   * Internal function without access restriction.
   */
  function _transferOwnership(address newOwner) internal virtual {
    address oldOwner = _owner;
    _owner = newOwner;
    emit OwnershipTransferred(oldOwner, newOwner);
  }
}
BokkyPooBahsDateTimeLibrary.sol 443 lines
// SPDX-License-Identifier: MIT
// https://raw.githubusercontent.com/bokkypoobah/BokkyPooBahsDateTimeLibrary/1dc26f977c57a6ba3ed6d7c53cafdb191e7e59ae/contracts/BokkyPooBahsDateTimeLibrary.sol
pragma solidity >=0.6.0 <0.9.0;

// ----------------------------------------------------------------------------
// BokkyPooBah's DateTime Library v1.01
//
// A gas-efficient Solidity date and time library
//
// https://github.com/bokkypoobah/BokkyPooBahsDateTimeLibrary
//
// Tested date range 1970/01/01 to 2345/12/31
//
// Conventions:
// Unit      | Range         | Notes
// :-------- |:-------------:|:-----
// timestamp | >= 0          | Unix timestamp, number of seconds since 1970/01/01 00:00:00 UTC
// year      | 1970 ... 2345 |
// month     | 1 ... 12      |
// day       | 1 ... 31      |
// hour      | 0 ... 23      |
// minute    | 0 ... 59      |
// second    | 0 ... 59      |
// dayOfWeek | 1 ... 7       | 1 = Monday, ..., 7 = Sunday
//
//
// Enjoy. (c) BokkyPooBah / Bok Consulting Pty Ltd 2018-2019. The MIT Licence.
// ----------------------------------------------------------------------------

library BokkyPooBahsDateTimeLibrary {
  uint constant SECONDS_PER_DAY = 24 * 60 * 60;
  uint constant SECONDS_PER_HOUR = 60 * 60;
  uint constant SECONDS_PER_MINUTE = 60;
  int constant OFFSET19700101 = 2440588;

  uint constant DOW_MON = 1;
  uint constant DOW_TUE = 2;
  uint constant DOW_WED = 3;
  uint constant DOW_THU = 4;
  uint constant DOW_FRI = 5;
  uint constant DOW_SAT = 6;
  uint constant DOW_SUN = 7;

  // ------------------------------------------------------------------------
  // Calculate the number of days from 1970/01/01 to year/month/day using
  // the date conversion algorithm from
  //   https://aa.usno.navy.mil/faq/JD_formula.html
  // and subtracting the offset 2440588 so that 1970/01/01 is day 0
  //
  // days = day
  //      - 32075
  //      + 1461 * (year + 4800 + (month - 14) / 12) / 4
  //      + 367 * (month - 2 - (month - 14) / 12 * 12) / 12
  //      - 3 * ((year + 4900 + (month - 14) / 12) / 100) / 4
  //      - offset
  // ------------------------------------------------------------------------
  function _daysFromDate(
    uint year,
    uint month,
    uint day
  ) internal pure returns (uint _days) {
    require(year >= 1970);
    int _year = int(year);
    int _month = int(month);
    int _day = int(day);

    int __days = _day -
      32075 +
      (1461 * (_year + 4800 + (_month - 14) / 12)) /
      4 +
      (367 * (_month - 2 - ((_month - 14) / 12) * 12)) /
      12 -
      (3 * ((_year + 4900 + (_month - 14) / 12) / 100)) /
      4 -
      OFFSET19700101;

    _days = uint(__days);
  }

  // ------------------------------------------------------------------------
  // Calculate year/month/day from the number of days since 1970/01/01 using
  // the date conversion algorithm from
  //   http://aa.usno.navy.mil/faq/docs/JD_Formula.php
  // and adding the offset 2440588 so that 1970/01/01 is day 0
  //
  // int L = days + 68569 + offset
  // int N = 4 * L / 146097
  // L = L - (146097 * N + 3) / 4
  // year = 4000 * (L + 1) / 1461001
  // L = L - 1461 * year / 4 + 31
  // month = 80 * L / 2447
  // dd = L - 2447 * month / 80
  // L = month / 11
  // month = month + 2 - 12 * L
  // year = 100 * (N - 49) + year + L
  // ------------------------------------------------------------------------
  function _daysToDate(
    uint _days
  ) internal pure returns (uint year, uint month, uint day) {
    int __days = int(_days);

    int L = __days + 68569 + OFFSET19700101;
    int N = (4 * L) / 146097;
    L = L - (146097 * N + 3) / 4;
    int _year = (4000 * (L + 1)) / 1461001;
    L = L - (1461 * _year) / 4 + 31;
    int _month = (80 * L) / 2447;
    int _day = L - (2447 * _month) / 80;
    L = _month / 11;
    _month = _month + 2 - 12 * L;
    _year = 100 * (N - 49) + _year + L;

    year = uint(_year);
    month = uint(_month);
    day = uint(_day);
  }

  function timestampFromDate(
    uint year,
    uint month,
    uint day
  ) internal pure returns (uint timestamp) {
    timestamp = _daysFromDate(year, month, day) * SECONDS_PER_DAY;
  }
  function timestampFromDateTime(
    uint year,
    uint month,
    uint day,
    uint hour,
    uint minute,
    uint second
  ) internal pure returns (uint timestamp) {
    timestamp =
      _daysFromDate(year, month, day) *
      SECONDS_PER_DAY +
      hour *
      SECONDS_PER_HOUR +
      minute *
      SECONDS_PER_MINUTE +
      second;
  }
  function timestampToDate(
    uint timestamp
  ) internal pure returns (uint year, uint month, uint day) {
    (year, month, day) = _daysToDate(timestamp / SECONDS_PER_DAY);
  }
  function timestampToDateTime(
    uint timestamp
  )
    internal
    pure
    returns (
      uint year,
      uint month,
      uint day,
      uint hour,
      uint minute,
      uint second
    )
  {
    (year, month, day) = _daysToDate(timestamp / SECONDS_PER_DAY);
    uint secs = timestamp % SECONDS_PER_DAY;
    hour = secs / SECONDS_PER_HOUR;
    secs = secs % SECONDS_PER_HOUR;
    minute = secs / SECONDS_PER_MINUTE;
    second = secs % SECONDS_PER_MINUTE;
  }

  function isValidDate(
    uint year,
    uint month,
    uint day
  ) internal pure returns (bool valid) {
    if (year >= 1970 && month > 0 && month <= 12) {
      uint daysInMonth = _getDaysInMonth(year, month);
      if (day > 0 && day <= daysInMonth) {
        valid = true;
      }
    }
  }
  function isValidDateTime(
    uint year,
    uint month,
    uint day,
    uint hour,
    uint minute,
    uint second
  ) internal pure returns (bool valid) {
    if (isValidDate(year, month, day)) {
      if (hour < 24 && minute < 60 && second < 60) {
        valid = true;
      }
    }
  }
  function isLeapYear(uint timestamp) internal pure returns (bool leapYear) {
    (uint year, , ) = _daysToDate(timestamp / SECONDS_PER_DAY);
    leapYear = _isLeapYear(year);
  }
  function _isLeapYear(uint year) internal pure returns (bool leapYear) {
    leapYear = ((year % 4 == 0) && (year % 100 != 0)) || (year % 400 == 0);
  }
  function isWeekDay(uint timestamp) internal pure returns (bool weekDay) {
    weekDay = getDayOfWeek(timestamp) <= DOW_FRI;
  }
  function isWeekEnd(uint timestamp) internal pure returns (bool weekEnd) {
    weekEnd = getDayOfWeek(timestamp) >= DOW_SAT;
  }
  function getDaysInMonth(
    uint timestamp
  ) internal pure returns (uint daysInMonth) {
    (uint year, uint month, ) = _daysToDate(timestamp / SECONDS_PER_DAY);
    daysInMonth = _getDaysInMonth(year, month);
  }
  function _getDaysInMonth(
    uint year,
    uint month
  ) internal pure returns (uint daysInMonth) {
    if (
      month == 1 ||
      month == 3 ||
      month == 5 ||
      month == 7 ||
      month == 8 ||
      month == 10 ||
      month == 12
    ) {
      daysInMonth = 31;
    } else if (month != 2) {
      daysInMonth = 30;
    } else {
      daysInMonth = _isLeapYear(year) ? 29 : 28;
    }
  }
  // 1 = Monday, 7 = Sunday
  function getDayOfWeek(uint timestamp) internal pure returns (uint dayOfWeek) {
    uint _days = timestamp / SECONDS_PER_DAY;
    dayOfWeek = ((_days + 3) % 7) + 1;
  }

  function getYear(uint timestamp) internal pure returns (uint year) {
    (year, , ) = _daysToDate(timestamp / SECONDS_PER_DAY);
  }
  function getMonth(uint timestamp) internal pure returns (uint month) {
    (, month, ) = _daysToDate(timestamp / SECONDS_PER_DAY);
  }
  function getDay(uint timestamp) internal pure returns (uint day) {
    (, , day) = _daysToDate(timestamp / SECONDS_PER_DAY);
  }
  function getHour(uint timestamp) internal pure returns (uint hour) {
    uint secs = timestamp % SECONDS_PER_DAY;
    hour = secs / SECONDS_PER_HOUR;
  }
  function getMinute(uint timestamp) internal pure returns (uint minute) {
    uint secs = timestamp % SECONDS_PER_HOUR;
    minute = secs / SECONDS_PER_MINUTE;
  }
  function getSecond(uint timestamp) internal pure returns (uint second) {
    second = timestamp % SECONDS_PER_MINUTE;
  }

  function addYears(
    uint timestamp,
    uint _years
  ) internal pure returns (uint newTimestamp) {
    (uint year, uint month, uint day) = _daysToDate(
      timestamp / SECONDS_PER_DAY
    );
    year += _years;
    uint daysInMonth = _getDaysInMonth(year, month);
    if (day > daysInMonth) {
      day = daysInMonth;
    }
    newTimestamp =
      _daysFromDate(year, month, day) *
      SECONDS_PER_DAY +
      (timestamp % SECONDS_PER_DAY);
    require(newTimestamp >= timestamp);
  }
  function addMonths(
    uint timestamp,
    uint _months
  ) internal pure returns (uint newTimestamp) {
    (uint year, uint month, uint day) = _daysToDate(
      timestamp / SECONDS_PER_DAY
    );
    month += _months;
    year += (month - 1) / 12;
    month = ((month - 1) % 12) + 1;
    uint daysInMonth = _getDaysInMonth(year, month);
    if (day > daysInMonth) {
      day = daysInMonth;
    }
    newTimestamp =
      _daysFromDate(year, month, day) *
      SECONDS_PER_DAY +
      (timestamp % SECONDS_PER_DAY);
    require(newTimestamp >= timestamp);
  }
  function addDays(
    uint timestamp,
    uint _days
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp + _days * SECONDS_PER_DAY;
    require(newTimestamp >= timestamp);
  }
  function addHours(
    uint timestamp,
    uint _hours
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp + _hours * SECONDS_PER_HOUR;
    require(newTimestamp >= timestamp);
  }
  function addMinutes(
    uint timestamp,
    uint _minutes
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp + _minutes * SECONDS_PER_MINUTE;
    require(newTimestamp >= timestamp);
  }
  function addSeconds(
    uint timestamp,
    uint _seconds
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp + _seconds;
    require(newTimestamp >= timestamp);
  }

  function subYears(
    uint timestamp,
    uint _years
  ) internal pure returns (uint newTimestamp) {
    (uint year, uint month, uint day) = _daysToDate(
      timestamp / SECONDS_PER_DAY
    );
    year -= _years;
    uint daysInMonth = _getDaysInMonth(year, month);
    if (day > daysInMonth) {
      day = daysInMonth;
    }
    newTimestamp =
      _daysFromDate(year, month, day) *
      SECONDS_PER_DAY +
      (timestamp % SECONDS_PER_DAY);
    require(newTimestamp <= timestamp);
  }
  function subMonths(
    uint timestamp,
    uint _months
  ) internal pure returns (uint newTimestamp) {
    (uint year, uint month, uint day) = _daysToDate(
      timestamp / SECONDS_PER_DAY
    );
    uint yearMonth = year * 12 + (month - 1) - _months;
    year = yearMonth / 12;
    month = (yearMonth % 12) + 1;
    uint daysInMonth = _getDaysInMonth(year, month);
    if (day > daysInMonth) {
      day = daysInMonth;
    }
    newTimestamp =
      _daysFromDate(year, month, day) *
      SECONDS_PER_DAY +
      (timestamp % SECONDS_PER_DAY);
    require(newTimestamp <= timestamp);
  }
  function subDays(
    uint timestamp,
    uint _days
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp - _days * SECONDS_PER_DAY;
    require(newTimestamp <= timestamp);
  }
  function subHours(
    uint timestamp,
    uint _hours
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp - _hours * SECONDS_PER_HOUR;
    require(newTimestamp <= timestamp);
  }
  function subMinutes(
    uint timestamp,
    uint _minutes
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp - _minutes * SECONDS_PER_MINUTE;
    require(newTimestamp <= timestamp);
  }
  function subSeconds(
    uint timestamp,
    uint _seconds
  ) internal pure returns (uint newTimestamp) {
    newTimestamp = timestamp - _seconds;
    require(newTimestamp <= timestamp);
  }

  function diffYears(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _years) {
    require(fromTimestamp <= toTimestamp);
    (uint fromYear, , ) = _daysToDate(fromTimestamp / SECONDS_PER_DAY);
    (uint toYear, , ) = _daysToDate(toTimestamp / SECONDS_PER_DAY);
    _years = toYear - fromYear;
  }
  function diffMonths(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _months) {
    require(fromTimestamp <= toTimestamp);
    (uint fromYear, uint fromMonth, ) = _daysToDate(
      fromTimestamp / SECONDS_PER_DAY
    );
    (uint toYear, uint toMonth, ) = _daysToDate(toTimestamp / SECONDS_PER_DAY);
    _months = toYear * 12 + toMonth - fromYear * 12 - fromMonth;
  }
  function diffDays(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _days) {
    require(fromTimestamp <= toTimestamp);
    _days = (toTimestamp - fromTimestamp) / SECONDS_PER_DAY;
  }
  function diffHours(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _hours) {
    require(fromTimestamp <= toTimestamp);
    _hours = (toTimestamp - fromTimestamp) / SECONDS_PER_HOUR;
  }
  function diffMinutes(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _minutes) {
    require(fromTimestamp <= toTimestamp);
    _minutes = (toTimestamp - fromTimestamp) / SECONDS_PER_MINUTE;
  }
  function diffSeconds(
    uint fromTimestamp,
    uint toTimestamp
  ) internal pure returns (uint _seconds) {
    require(fromTimestamp <= toTimestamp);
    _seconds = toTimestamp - fromTimestamp;
  }
}
Context.sol 24 lines
// SPDX-License-Identifier: MIT
// OpenZeppelin Contracts v4.4.1 (utils/Context.sol)

pragma solidity ^0.8.0;

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

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

Read Contract

checkIsValidHours 0xe8c7e728
owner 0x8da5cb5b → address
pendingOwner 0xe30c3978 → address
timezoneOffset 0x6c7c1cbb → int256

Write Contract 4 functions

These functions modify contract state and require a wallet transaction to execute.

acceptOwnership 0x79ba5097
No parameters
renounceOwnership 0x715018a6
No parameters
setTimezoneOffset 0x5b2ec32b
int256 _timezoneOffset
transferOwnership 0xf2fde38b
address newOwner

Recent Transactions

This address has 1 on-chain transactions, but only 0.7% of the chain is indexed. Transactions will appear as indexing progresses. View on Etherscan →