HelenOS sources
This source file includes following definitions.
- count
- zero
- min
- max
- time_since_epoch
- min
- max
- zero
- min
- max
- now
- to_time_t
- from_time_t
- now
#ifndef LIBCPP_BITS_CHRONO
#define LIBCPP_BITS_CHRONO
#include <ctime>
#include <limits>
#include <ratio>
#include <type_traits>
namespace std::chrono
{
template<class Rep, class Period = ratio<1>>
class duration;
template<class ToDuration, class Rep, class Period>
constexpr ToDuration duration_cast(const duration<Rep, Period>& dur);
template<class Rep>
struct duration_values;
template<class Rep, class Period>
class duration
{
public:
using rep = Rep;
using period = Period;
constexpr duration() = default;
template<class Rep2>
constexpr explicit duration(const Rep2& r)
: rep_{r}
{ }
template<class Rep2, class Period2>
constexpr duration(const duration<Rep2, Period2>& other)
: rep_{duration_cast<duration>(other).count()}
{ }
~duration() = default;
duration(const duration&) = default;
duration& operator=(const duration&) = default;
constexpr rep count() const
{
return rep_;
}
constexpr duration operator+() const
{
return *this;
}
constexpr duration operator-() const
{
return duration{-rep_};
}
duration& operator++()
{
++rep_;
return *this;
}
duration operator++(int)
{
return duration{rep_++};
}
duration& operator--()
{
--rep_;
*this;
}
duration operator--(int)
{
return duration{rep_--};
}
duration& operator+=(const duration& rhs)
{
rep_ += rhs.count();
return *this;
}
duration& operator-=(const duration& rhs)
{
rep_ -= rhs.count();
return *this;
}
duration& operator*=(const rep& rhs)
{
rep_ *= rhs;
return *this;
}
duration& operator/=(const rep& rhs)
{
rep_ /= rhs;
return *this;
}
duration& operator%=(const rep& rhs)
{
rep_ %= rhs;
return *this;
}
duration& operator%=(const duration& rhs)
{
rep_ %= rhs.count();
return *this;
}
static constexpr duration zero()
{
return duration{duration_values<rep>::zero()};
}
static constexpr duration min()
{
return duration{duration_values<rep>::min()};
}
static constexpr duration max()
{
return duration{duration_values<rep>::max()};
}
private:
rep rep_;
};
template<class Clock, class Duration = typename Clock::duration>
class time_point
{
public:
using clock = Clock;
using duration = Duration;
using rep = typename duration::rep;
using period = typename duration::period;
constexpr time_point()
: duration_{duration::zero()}
{ }
constexpr explicit time_point(const duration& d)
: duration_{d}
{ }
template<class Duration2>
constexpr time_point(const time_point<clock, Duration2>& other)
: duration_{static_cast<duration>(other.time_since_epoch())}
{ }
constexpr duration time_since_epoch() const
{
return duration_;
}
time_point& operator+=(const duration& rhs)
{
duration_ += rhs;
return *this;
}
time_point& operator-=(const duration& rhs)
{
duration_ -= rhs;
return *this;
}
static constexpr time_point min()
{
return time_point{duration::min()};
}
static constexpr time_point max()
{
return time_point{duration::max()};
}
private:
duration duration_;
};
}
namespace std
{
template<class Rep1, class Period1, class Rep2, class Period2>
struct common_type<chrono::duration<Rep1, Period1>, chrono::duration<Rep2, Period2>>
{
using type = chrono::duration<
common_type_t<Rep1, Rep2>,
ratio<aux::gcd_v<Period1::num, Period2::num>, aux::lcm_v<Period1::den, Period2::den>>
>;
};
template<class Clock, class Duration1, class Duration2>
struct common_type<chrono::time_point<Clock, Duration1>, chrono::time_point<Clock, Duration2>>
{
using type = chrono::time_point<Clock, common_type_t<Duration1, Duration2>>;
};
}
namespace std::chrono
{
template<class Rep>
struct treat_as_floating_point: is_floating_point<Rep>
{ };
template<class Rep>
struct duration_values
{
static constexpr Rep zero()
{
return Rep(0);
}
static constexpr Rep min()
{
return numeric_limits<Rep>::lowest();
}
static constexpr Rep max()
{
return numeric_limits<Rep>::max();
}
};
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>
operator+(const duration<Rep1, Period1>& lhs, const duration<Rep2, Period2>& rhs)
{
using CD = common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>;
return CD(CD(lhs).count() + CD(rhs).count());
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>
operator-(const duration<Rep1, Period1>& lhs, const duration<Rep2, Period2>& rhs)
{
using CD = common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>;
return CD(CD(lhs).count() - CD(rhs).count());
}
template<class Rep1, class Period, class Rep2>
constexpr duration<common_type_t<Rep1, Rep2>, Period>
operator*(const duration<Rep1, Period>& dur, const Rep2& rep)
{
using CD = duration<common_type_t<Rep1, Rep2>, Period>;
return CD(CD(dur).count() * rep);
}
template<class Rep1, class Period, class Rep2>
constexpr duration<common_type_t<Rep1, Rep2>, Period>
operator*(const Rep2& rep, const duration<Rep1, Period>& dur)
{
return dur * rep;
}
template<class Rep1, class Period, class Rep2>
constexpr duration<common_type_t<Rep1, Rep2>, Period>
operator/(const duration<Rep1, Period>& dur, const Rep2& rep)
{
using CD = duration<common_type_t<Rep1, Rep2>, Period>;
return CD(CD(dur).count() / rep);
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr common_type_t<Rep1, Rep2>
operator/(const duration<Rep1, Period1>& lhs, const duration<Rep2, Period2>& rhs)
{
using CD = common_type_t<Rep1, Rep2>;
return CD(lhs).count() / CD(rhs).count();
}
template<class Rep1, class Period, class Rep2>
constexpr duration<common_type_t<Rep1, Rep2>, Period>
operator%(const duration<Rep1, Period>& dur, const Rep2& rep)
{
using CD = duration<common_type_t<Rep1, Rep2>, Period>;
return CD(CD(dur).count() / rep);
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>
operator%(const duration<Rep1, Period1>& lhs, const duration<Rep2, Period2>& rhs)
{
using CD = common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>;
return CD(CD(lhs).count() % CD(rhs).count());
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator==(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
using CT = common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>;
return CT(lhs).count() == CT(rhs).count();
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator!=(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
return !(lhs == rhs);
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator<(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
using CT = common_type_t<duration<Rep1, Period1>, duration<Rep2, Period2>>;
return CT(lhs).count() < CT(rhs).count();
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator<=(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
return !(rhs < lhs);
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator>(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
return rhs < lhs;
}
template<class Rep1, class Period1, class Rep2, class Period2>
constexpr bool operator>=(const duration<Rep1, Period1>& lhs,
const duration<Rep2, Period2>& rhs)
{
return !(lhs < rhs);
}
template<class ToDuration, class Rep, class Period>
constexpr ToDuration duration_cast(const duration<Rep, Period>& dur)
{
using CF = ratio_divide<Period, typename ToDuration::period>;
using CR = typename common_type<typename ToDuration::rep, Rep, intmax_t>::type;
using to_rep = typename ToDuration::rep;
if constexpr (CF::num == 1 && CF::den == 1)
return ToDuration(static_cast<to_rep>(dur.count()));
else if constexpr (CF::num != 1 && CF::den == 1)
{
return ToDuration(
static_cast<to_rep>(
static_cast<CR>(dur.count()) * static_cast<CR>(CF::num)
)
);
}
else if constexpr (CF::num == 1 && CF::den != 1)
{
return ToDuration(
static_cast<to_rep>(
static_cast<CR>(dur.count()) / static_cast<CR>(CF::den)
)
);
}
else
{
return ToDuration(
static_cast<to_rep>(
static_cast<CR>(dur.count()) * static_cast<CR>(CF::num)
/ static_cast<CR>(CF::den)
)
);
}
}
using nanoseconds = duration<int64_t, nano>;
using microseconds = duration<int64_t, micro>;
using milliseconds = duration<int64_t, milli>;
using seconds = duration<int64_t>;
using minutes = duration<int32_t, ratio<60>>;
using hours = duration<int32_t, ratio<3600>>;
template<class Clock, class Duration1, class Rep2, class Period2>
constexpr time_point<Clock, common_type_t<Duration1, duration<Rep2, Period2>>>
operator+(const time_point<Clock, Duration1>& lhs, const duration<Rep2, Period2>& rhs)
{
using CT = time_point<Clock, common_type_t<Duration1, duration<Rep2, Period2>>>;
return CT(lhs.time_since_epoch() + rhs);
}
template<class Rep1, class Period1, class Clock, class Duration2>
constexpr time_point<Clock, common_type_t<duration<Rep1, Period1>, Duration2>>
operator+(const duration<Rep1, Period1>& lhs, const time_point<Clock, Duration2>& rhs)
{
return rhs + lhs;
}
template<class Clock, class Duration1, class Rep2, class Period2>
constexpr time_point<Clock, common_type_t<Duration1, duration<Rep2, Period2>>>
operator-(const time_point<Clock, Duration1>& lhs, const duration<Rep2, Period2>& rhs)
{
return lhs + (-rhs);
}
template<class Clock, class Duration1, class Duration2>
constexpr common_type_t<Duration1, Duration2>
operator-(const time_point<Clock, Duration1>& lhs, const time_point<Clock, Duration2>& rhs)
{
return lhs.time_since_epoch() - rhs.time_since_epoch();
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator==(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return lhs.time_since_epoch() == rhs.time_since_epoch();
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator!=(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return !(lhs == rhs);
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator<(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return lhs.time_since_epoch() < rhs.time_since_epoch();
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator<=(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return !(rhs < lhs);
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator>(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return rhs < lhs;
}
template<class Clock, class Duration1, class Duration2>
constexpr bool operator>=(const time_point<Clock, Duration1>& lhs,
const time_point<Clock, Duration2>& rhs)
{
return !(lhs < rhs);
}
template<class ToDuration, class Clock, class Duration>
constexpr time_point<Clock, ToDuration>
time_point_cast(const time_point<Clock, Duration>& tp)
{
return time_point<Clock, ToDuration>(
duration_cast<ToDuration>(tp.time_since_epoch())
);
}
class system_clock
{
public:
using rep = int64_t;
using period = micro;
using duration = chrono::duration<rep, period>;
using time_point = chrono::time_point<system_clock>;
static constexpr bool is_steady = true;
static time_point now()
{
::std::timespec ts{};
::helenos::getrealtime(&ts);
rep time = NSEC2USEC(ts.tv_nsec);
time += (ts.tv_sec * 1'000'000ul);
return time_point{duration{time - epoch_usecs}};
}
static time_t to_time_t(const time_point& tp)
{
return time_t{};
}
static time_point from_time_t(time_t tt)
{
return time_point{};
}
private:
static constexpr rep epoch_usecs{11644473600ul * 1'000'000ul};
};
class steady_clock
{
public:
using rep = int64_t;
using period = micro;
using duration = chrono::duration<rep, period>;
using time_point = chrono::time_point<steady_clock>;
static constexpr bool is_steady = true;
static time_point now()
{
::std::timespec ts{};
::helenos::getuptime(&ts);
rep time = NSEC2USEC(ts.tv_nsec);
time += (ts.tv_sec * 1'000'000ul);
return time_point{duration{time}};
}
};
using high_resolution_clock = system_clock;
}
namespace std
{
inline namespace literals
{
inline namespace chrono_literals
{
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wliteral-suffix"
constexpr chrono::hours operator ""h(unsigned long long hrs)
{
return chrono::hours{static_cast<chrono::hours::rep>(hrs)};
}
constexpr chrono::duration<long double, ratio<3600>> operator ""h(long double hrs)
{
return chrono::duration<long double, ratio<3600>>{hrs};
}
constexpr chrono::minutes operator ""m(unsigned long long mins)
{
return chrono::minutes{static_cast<chrono::minutes::rep>(mins)};
}
constexpr chrono::duration<long double, ratio<60>> operator ""m(long double mins)
{
return chrono::duration<long double, ratio<60>>{mins};
}
constexpr chrono::seconds operator ""s(unsigned long long secs)
{
return chrono::seconds{static_cast<chrono::seconds::rep>(secs)};
}
constexpr chrono::duration<long double, ratio<1>> operator ""s(long double secs)
{
return chrono::duration<long double, ratio<1>>{secs};
}
constexpr chrono::milliseconds operator ""ms(unsigned long long msecs)
{
return chrono::milliseconds{static_cast<chrono::milliseconds::rep>(msecs)};
}
constexpr chrono::duration<long double, milli> operator ""ms(long double msecs)
{
return chrono::duration<long double, milli>{msecs};
}
constexpr chrono::microseconds operator ""us(unsigned long long usecs)
{
return chrono::microseconds{static_cast<chrono::microseconds::rep>(usecs)};
}
constexpr chrono::duration<long double, micro> operator ""us(long double usecs)
{
return chrono::duration<long double, micro>{usecs};
}
constexpr chrono::nanoseconds operator ""ns(unsigned long long nsecs)
{
return chrono::nanoseconds{static_cast<chrono::nanoseconds::rep>(nsecs)};
}
constexpr chrono::duration<long double, nano> operator ""ns(long double nsecs)
{
return chrono::duration<long double, nano>{nsecs};
}
#pragma GCC diagnostic pop
}
}
namespace chrono
{
using namespace literals::chrono_literals;
}
}
#endif
HelenOS homepage, sources at GitHub