diff options
Diffstat (limited to '')
-rw-r--r-- | src/include/encoding.h | 49 |
1 files changed, 40 insertions, 9 deletions
diff --git a/src/include/encoding.h b/src/include/encoding.h index 40ba9d39c..08c67c33e 100644 --- a/src/include/encoding.h +++ b/src/include/encoding.h @@ -14,6 +14,7 @@ #ifndef CEPH_ENCODING_H #define CEPH_ENCODING_H +#include <concepts> #include <set> #include <map> #include <deque> @@ -322,10 +323,11 @@ inline void decode_nohead(int len, bufferlist& s, bufferlist::const_iterator& p) p.copy(len, s); } -// Time, since the templates are defined in std::chrono +// Time, since the templates are defined in std::chrono. The default encodings +// for time_point and duration are backward-compatible with utime_t, but +// truncate seconds to 32 bits so are not guaranteed to round-trip. -template<typename Clock, typename Duration, - typename std::enable_if_t<converts_to_timespec_v<Clock>>* = nullptr> +template<clock_with_timespec Clock, typename Duration> void encode(const std::chrono::time_point<Clock, Duration>& t, ceph::bufferlist &bl) { auto ts = Clock::to_timespec(t); @@ -336,8 +338,7 @@ void encode(const std::chrono::time_point<Clock, Duration>& t, encode(ns, bl); } -template<typename Clock, typename Duration, - typename std::enable_if_t<converts_to_timespec_v<Clock>>* = nullptr> +template<clock_with_timespec Clock, typename Duration> void decode(std::chrono::time_point<Clock, Duration>& t, bufferlist::const_iterator& p) { uint32_t s; @@ -351,8 +352,7 @@ void decode(std::chrono::time_point<Clock, Duration>& t, t = Clock::from_timespec(ts); } -template<typename Rep, typename Period, - typename std::enable_if_t<std::is_integral_v<Rep>>* = nullptr> +template<std::integral Rep, typename Period> void encode(const std::chrono::duration<Rep, Period>& d, ceph::bufferlist &bl) { using namespace std::chrono; @@ -362,8 +362,7 @@ void encode(const std::chrono::duration<Rep, Period>& d, encode(ns, bl); } -template<typename Rep, typename Period, - typename std::enable_if_t<std::is_integral_v<Rep>>* = nullptr> +template<std::integral Rep, typename Period> void decode(std::chrono::duration<Rep, Period>& d, bufferlist::const_iterator& p) { int32_t s; @@ -373,6 +372,38 @@ void decode(std::chrono::duration<Rep, Period>& d, d = std::chrono::seconds(s) + std::chrono::nanoseconds(ns); } +// Provide encodings for chrono::time_point and duration that use +// the underlying representation so are guaranteed to round-trip. + +template <std::integral Rep, typename Period> +void round_trip_encode(const std::chrono::duration<Rep, Period>& d, + ceph::bufferlist &bl) { + const Rep r = d.count(); + encode(r, bl); +} + +template <std::integral Rep, typename Period> +void round_trip_decode(std::chrono::duration<Rep, Period>& d, + bufferlist::const_iterator& p) { + Rep r; + decode(r, p); + d = std::chrono::duration<Rep, Period>(r); +} + +template <typename Clock, typename Duration> +void round_trip_encode(const std::chrono::time_point<Clock, Duration>& t, + ceph::bufferlist &bl) { + round_trip_encode(t.time_since_epoch(), bl); +} + +template <typename Clock, typename Duration> +void round_trip_decode(std::chrono::time_point<Clock, Duration>& t, + bufferlist::const_iterator& p) { + Duration dur; + round_trip_decode(dur, p); + t = std::chrono::time_point<Clock, Duration>(dur); +} + // ----------------------------- // STL container types |