X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=folly%2FChrono.h;h=852a74b7f6d96ae877446056cdeb44dc79b9f814;hb=79b78eaaf88ead9fa6543822c193b4e86d0e2395;hp=1a9dfa54631285b7e2e3dac540f5fcf15054c7ca;hpb=22afce906d7e98d95f8c45c3301072d9fd891d41;p=folly.git diff --git a/folly/Chrono.h b/folly/Chrono.h index 1a9dfa54..852a74b7 100644 --- a/folly/Chrono.h +++ b/folly/Chrono.h @@ -1,5 +1,5 @@ /* - * Copyright 2014 Facebook, Inc. + * Copyright 2017 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -14,20 +14,141 @@ * limitations under the License. */ -// Wrapper around that hides away some gcc 4.6 issues -#ifndef FOLLY_CHRONO_H_ -#define FOLLY_CHRONO_H_ +#pragma once #include -#include "folly/Portability.h" - -// gcc 4.6 uses an obsolete name for steady_clock, although the implementation -// is the same -#if __GNUC_PREREQ(4, 6) && !__GNUC_PREREQ(4, 7) -namespace std { namespace chrono { -typedef monotonic_clock steady_clock; -}} // namespaces -#endif +#include + +/*** + * include or backport: + * * std::chrono::ceil + * * std::chrono::floor + * * std::chrono::round + */ + +#if __cpp_lib_chrono >= 201510 || _MSC_VER + +namespace folly { +namespace chrono { + +/* using override */ using std::chrono::ceil; +/* using override */ using std::chrono::floor; +/* using override */ using std::chrono::round; +} +} + +#else + +namespace folly { +namespace chrono { + +namespace detail { + +// from: http://en.cppreference.com/w/cpp/chrono/duration/ceil, CC-BY-SA +template +struct is_duration : std::false_type {}; +template +struct is_duration> : std::true_type {}; + +template +constexpr To ceil_impl(Duration const& d, To const& t) { + return t < d ? t + To{1} : t; +} -#endif /* FOLLY_CHRONO_H_ */ +template +constexpr To floor_impl(Duration const& d, To const& t) { + return t > d ? t - To{1} : t; +} +template +constexpr To round_impl(To const& t0, To const& t1, Diff diff0, Diff diff1) { + return diff0 < diff1 ? t0 : diff1 < diff0 ? t1 : t0.count() & 1 ? t1 : t0; +} + +template +constexpr To round_impl(Duration const& d, To const& t0, To const& t1) { + return round_impl(t0, t1, d - t0, t1 - d); +} + +template +constexpr To round_impl(Duration const& d, To const& t0) { + return round_impl(d, t0, t0 + To{1}); +} +} + +// mimic: std::chrono::ceil, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/duration/ceil, CC-BY-SA +template < + typename To, + typename Rep, + typename Period, + typename = typename std::enable_if::value>::type> +constexpr To ceil(std::chrono::duration const& d) { + return detail::ceil_impl(d, std::chrono::duration_cast(d)); +} + +// mimic: std::chrono::ceil, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/time_point/ceil, CC-BY-SA +template < + typename To, + typename Clock, + typename Duration, + typename = typename std::enable_if::value>::type> +constexpr std::chrono::time_point ceil( + std::chrono::time_point const& tp) { + return std::chrono::time_point{ceil(tp.time_since_epoch())}; +} + +// mimic: std::chrono::floor, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/duration/floor, CC-BY-SA +template < + typename To, + typename Rep, + typename Period, + typename = typename std::enable_if::value>::type> +constexpr To floor(std::chrono::duration const& d) { + return detail::floor_impl(d, std::chrono::duration_cast(d)); +} + +// mimic: std::chrono::floor, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/time_point/floor, CC-BY-SA +template < + typename To, + typename Clock, + typename Duration, + typename = typename std::enable_if::value>::type> +constexpr std::chrono::time_point floor( + std::chrono::time_point const& tp) { + return std::chrono::time_point{floor(tp.time_since_epoch())}; +} + +// mimic: std::chrono::round, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/duration/round, CC-BY-SA +template < + typename To, + typename Rep, + typename Period, + typename = typename std::enable_if< + detail::is_duration::value && + !std::chrono::treat_as_floating_point::value>::type> +constexpr To round(std::chrono::duration const& d) { + return detail::round_impl(d, floor(d)); +} + +// mimic: std::chrono::round, C++17 +// from: http://en.cppreference.com/w/cpp/chrono/time_point/round, CC-BY-SA +template < + typename To, + typename Clock, + typename Duration, + typename = typename std::enable_if< + detail::is_duration::value && + !std::chrono::treat_as_floating_point::value>::type> +constexpr std::chrono::time_point round( + std::chrono::time_point const& tp) { + return std::chrono::time_point{round(tp.time_since_epoch())}; +} +} +} + +#endif