master
  1// -*- C++ -*-
  2//===----------------------------------------------------------------------===//
  3//
  4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  5// See https://llvm.org/LICENSE.txt for license information.
  6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  7//
  8//===----------------------------------------------------------------------===//
  9
 10#ifndef _LIBCPP___CHRONO_TIME_POINT_H
 11#define _LIBCPP___CHRONO_TIME_POINT_H
 12
 13#include <__chrono/duration.h>
 14#include <__compare/ordering.h>
 15#include <__compare/three_way_comparable.h>
 16#include <__config>
 17#include <__type_traits/common_type.h>
 18#include <__type_traits/enable_if.h>
 19#include <__type_traits/is_convertible.h>
 20#include <limits>
 21
 22#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
 23#  pragma GCC system_header
 24#endif
 25
 26_LIBCPP_PUSH_MACROS
 27#include <__undef_macros>
 28
 29_LIBCPP_BEGIN_NAMESPACE_STD
 30
 31namespace chrono {
 32
 33template <class _Clock, class _Duration = typename _Clock::duration>
 34class time_point {
 35  static_assert(__is_duration_v<_Duration>, "Second template parameter of time_point must be a std::chrono::duration");
 36
 37public:
 38  typedef _Clock clock;
 39  typedef _Duration duration;
 40  typedef typename duration::rep rep;
 41  typedef typename duration::period period;
 42
 43private:
 44  duration __d_;
 45
 46public:
 47  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 time_point() : __d_(duration::zero()) {}
 48  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 explicit time_point(const duration& __d) : __d_(__d) {}
 49
 50  // conversions
 51  template <class _Duration2, __enable_if_t<is_convertible<_Duration2, duration>::value, int> = 0>
 52  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 time_point(const time_point<clock, _Duration2>& __t)
 53      : __d_(__t.time_since_epoch()) {}
 54
 55  // observer
 56
 57  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 duration time_since_epoch() const { return __d_; }
 58
 59  // arithmetic
 60
 61#if _LIBCPP_STD_VER >= 20
 62  _LIBCPP_HIDE_FROM_ABI constexpr time_point& operator++() {
 63    ++__d_;
 64    return *this;
 65  }
 66  _LIBCPP_HIDE_FROM_ABI constexpr time_point operator++(int) { return time_point{__d_++}; }
 67  _LIBCPP_HIDE_FROM_ABI constexpr time_point& operator--() {
 68    --__d_;
 69    return *this;
 70  }
 71  _LIBCPP_HIDE_FROM_ABI constexpr time_point operator--(int) { return time_point{__d_--}; }
 72#endif // _LIBCPP_STD_VER >= 20
 73
 74  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 time_point& operator+=(const duration& __d) {
 75    __d_ += __d;
 76    return *this;
 77  }
 78  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX17 time_point& operator-=(const duration& __d) {
 79    __d_ -= __d;
 80    return *this;
 81  }
 82
 83  // special values
 84
 85  _LIBCPP_HIDE_FROM_ABI static _LIBCPP_CONSTEXPR time_point min() _NOEXCEPT { return time_point(duration::min()); }
 86  _LIBCPP_HIDE_FROM_ABI static _LIBCPP_CONSTEXPR time_point max() _NOEXCEPT { return time_point(duration::max()); }
 87};
 88
 89} // namespace chrono
 90
 91template <class _Clock, class _Duration1, class _Duration2>
 92struct common_type<chrono::time_point<_Clock, _Duration1>, chrono::time_point<_Clock, _Duration2> > {
 93  typedef chrono::time_point<_Clock, typename common_type<_Duration1, _Duration2>::type> type;
 94};
 95
 96namespace chrono {
 97
 98template <class _ToDuration, class _Clock, class _Duration>
 99inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 time_point<_Clock, _ToDuration>
100time_point_cast(const time_point<_Clock, _Duration>& __t) {
101  return time_point<_Clock, _ToDuration>(chrono::duration_cast<_ToDuration>(__t.time_since_epoch()));
102}
103
104#if _LIBCPP_STD_VER >= 17
105template <class _ToDuration, class _Clock, class _Duration, enable_if_t<__is_duration_v<_ToDuration>, int> = 0>
106inline _LIBCPP_HIDE_FROM_ABI constexpr time_point<_Clock, _ToDuration> floor(const time_point<_Clock, _Duration>& __t) {
107  return time_point<_Clock, _ToDuration>{chrono::floor<_ToDuration>(__t.time_since_epoch())};
108}
109
110template <class _ToDuration, class _Clock, class _Duration, enable_if_t<__is_duration_v<_ToDuration>, int> = 0>
111inline _LIBCPP_HIDE_FROM_ABI constexpr time_point<_Clock, _ToDuration> ceil(const time_point<_Clock, _Duration>& __t) {
112  return time_point<_Clock, _ToDuration>{chrono::ceil<_ToDuration>(__t.time_since_epoch())};
113}
114
115template <class _ToDuration, class _Clock, class _Duration, enable_if_t<__is_duration_v<_ToDuration>, int> = 0>
116inline _LIBCPP_HIDE_FROM_ABI constexpr time_point<_Clock, _ToDuration> round(const time_point<_Clock, _Duration>& __t) {
117  return time_point<_Clock, _ToDuration>{chrono::round<_ToDuration>(__t.time_since_epoch())};
118}
119
120template <class _Rep, class _Period, enable_if_t<numeric_limits<_Rep>::is_signed, int> = 0>
121inline _LIBCPP_HIDE_FROM_ABI constexpr duration<_Rep, _Period> abs(duration<_Rep, _Period> __d) {
122  return __d >= __d.zero() ? +__d : -__d;
123}
124#endif // _LIBCPP_STD_VER >= 17
125
126// time_point ==
127
128template <class _Clock, class _Duration1, class _Duration2>
129inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
130operator==(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
131  return __lhs.time_since_epoch() == __rhs.time_since_epoch();
132}
133
134#if _LIBCPP_STD_VER <= 17
135
136// time_point !=
137
138template <class _Clock, class _Duration1, class _Duration2>
139inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
140operator!=(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
141  return !(__lhs == __rhs);
142}
143
144#endif // _LIBCPP_STD_VER <= 17
145
146// time_point <
147
148template <class _Clock, class _Duration1, class _Duration2>
149inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
150operator<(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
151  return __lhs.time_since_epoch() < __rhs.time_since_epoch();
152}
153
154// time_point >
155
156template <class _Clock, class _Duration1, class _Duration2>
157inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
158operator>(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
159  return __rhs < __lhs;
160}
161
162// time_point <=
163
164template <class _Clock, class _Duration1, class _Duration2>
165inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
166operator<=(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
167  return !(__rhs < __lhs);
168}
169
170// time_point >=
171
172template <class _Clock, class _Duration1, class _Duration2>
173inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 bool
174operator>=(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
175  return !(__lhs < __rhs);
176}
177
178#if _LIBCPP_STD_VER >= 20
179
180template <class _Clock, class _Duration1, three_way_comparable_with<_Duration1> _Duration2>
181_LIBCPP_HIDE_FROM_ABI constexpr auto
182operator<=>(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
183  return __lhs.time_since_epoch() <=> __rhs.time_since_epoch();
184}
185
186#endif // _LIBCPP_STD_VER >= 20
187
188// time_point operator+(time_point x, duration y);
189
190template <class _Clock, class _Duration1, class _Rep2, class _Period2>
191inline _LIBCPP_HIDE_FROM_ABI
192_LIBCPP_CONSTEXPR_SINCE_CXX14 time_point<_Clock, typename common_type<_Duration1, duration<_Rep2, _Period2> >::type>
193operator+(const time_point<_Clock, _Duration1>& __lhs, const duration<_Rep2, _Period2>& __rhs) {
194  typedef time_point<_Clock, typename common_type<_Duration1, duration<_Rep2, _Period2> >::type> _Tr;
195  return _Tr(__lhs.time_since_epoch() + __rhs);
196}
197
198// time_point operator+(duration x, time_point y);
199
200template <class _Rep1, class _Period1, class _Clock, class _Duration2>
201inline _LIBCPP_HIDE_FROM_ABI
202_LIBCPP_CONSTEXPR_SINCE_CXX14 time_point<_Clock, typename common_type<duration<_Rep1, _Period1>, _Duration2>::type>
203operator+(const duration<_Rep1, _Period1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
204  return __rhs + __lhs;
205}
206
207// time_point operator-(time_point x, duration y);
208
209template <class _Clock, class _Duration1, class _Rep2, class _Period2>
210inline _LIBCPP_HIDE_FROM_ABI
211_LIBCPP_CONSTEXPR_SINCE_CXX14 time_point<_Clock, typename common_type<_Duration1, duration<_Rep2, _Period2> >::type>
212operator-(const time_point<_Clock, _Duration1>& __lhs, const duration<_Rep2, _Period2>& __rhs) {
213  typedef time_point<_Clock, typename common_type<_Duration1, duration<_Rep2, _Period2> >::type> _Ret;
214  return _Ret(__lhs.time_since_epoch() - __rhs);
215}
216
217// duration operator-(time_point x, time_point y);
218
219template <class _Clock, class _Duration1, class _Duration2>
220inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX14 typename common_type<_Duration1, _Duration2>::type
221operator-(const time_point<_Clock, _Duration1>& __lhs, const time_point<_Clock, _Duration2>& __rhs) {
222  return __lhs.time_since_epoch() - __rhs.time_since_epoch();
223}
224
225} // namespace chrono
226
227_LIBCPP_END_NAMESPACE_STD
228
229_LIBCPP_POP_MACROS
230
231#endif // _LIBCPP___CHRONO_TIME_POINT_H