Program Listing for File Time_t.h
↰ Return to documentation for file (/tmp/ws/src/fastrtps/include/fastdds/rtps/common/Time_t.h
)
// Copyright 2019 Proyectos y Sistemas de Mantenimiento SL (eProsima).
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _FASTDDS_RTPS_TIME_T_H_
#define _FASTDDS_RTPS_TIME_T_H_
#include <fastrtps/fastrtps_dll.h>
#include <cmath>
#include <cstdint>
#include <iostream>
namespace eprosima {
namespace fastrtps {
struct RTPS_DllAPI Time_t
{
static constexpr int32_t INFINITE_SECONDS = 0x7fffffff;
static constexpr uint32_t INFINITE_NANOSECONDS = 0xffffffffu;
int32_t seconds;
uint32_t nanosec;
Time_t();
Time_t(
int32_t sec,
uint32_t nsec);
Time_t(
long double sec);
void fraction(
uint32_t frac);
uint32_t fraction() const;
int64_t to_ns() const;
inline bool is_infinite() const noexcept
{
return is_infinite(*this);
}
static void now(
Time_t& ret);
static inline constexpr bool is_infinite(
const Time_t& t) noexcept
{
return (INFINITE_SECONDS == t.seconds) || (INFINITE_NANOSECONDS == t.nanosec);
}
};
using Duration_t = Time_t;
namespace rtps {
class RTPS_DllAPI Time_t
{
public:
Time_t() = default;
Time_t(
int32_t sec,
uint32_t frac);
Time_t(
long double sec);
Time_t(
const eprosima::fastrtps::Time_t& time);
int64_t to_ns() const;
void from_ns(
int64_t nanosecs);
int32_t seconds() const;
int32_t& seconds();
void seconds(
int32_t sec);
uint32_t nanosec() const;
void nanosec(
uint32_t nanos);
uint32_t fraction() const;
void fraction(
uint32_t frac);
Duration_t to_duration_t() const;
void from_duration_t(
const Duration_t& duration);
static void now(
Time_t& ret);
private:
int32_t seconds_ = 0;
uint32_t fraction_ = 0;
uint32_t nanosec_ = 0;
void set_fraction(
uint32_t frac);
void set_nanosec(
uint32_t nanos);
};
#ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
static inline bool operator ==(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() != t2.seconds())
{
return false;
}
if (t1.fraction() != t2.fraction())
{
return false;
}
return true;
}
static inline bool operator !=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() != t2.seconds())
{
return true;
}
if (t1.fraction() != t2.fraction())
{
return true;
}
return false;
}
static inline bool operator <(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() < t2.seconds())
{
return true;
}
else if (t1.seconds() > t2.seconds())
{
return false;
}
else
{
if (t1.fraction() < t2.fraction())
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator >(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() > t2.seconds())
{
return true;
}
else if (t1.seconds() < t2.seconds())
{
return false;
}
else
{
if (t1.fraction() > t2.fraction())
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator <=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() < t2.seconds())
{
return true;
}
else if (t1.seconds() > t2.seconds())
{
return false;
}
else
{
if (t1.fraction() <= t2.fraction())
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator >=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds() > t2.seconds())
{
return true;
}
else if (t1.seconds() < t2.seconds())
{
return false;
}
else
{
if (t1.fraction() >= t2.fraction())
{
return true;
}
else
{
return false;
}
}
}
inline std::ostream& operator <<(
std::ostream& output,
const Time_t& t)
{
return output << t.seconds() << "." << t.nanosec();
}
inline std::istream& operator >>(
std::istream& input,
Time_t& t)
{
std::istream::sentry s(input);
if (s)
{
char point;
int32_t sec = 0;
uint32_t nano = 0;
std::ios_base::iostate excp_mask = input.exceptions();
try
{
input.exceptions(excp_mask | std::ios_base::failbit | std::ios_base::badbit);
input >> sec;
input >> point >> nano;
// nano could not be bigger or equal than 1 sec
if ( point != '.' || nano >= 1000000000 )
{
input.setstate(std::ios_base::failbit);
nano = 0;
}
}
catch (std::ios_base::failure& )
{
}
t.seconds(sec);
t.nanosec(nano);
input.exceptions(excp_mask);
}
return input;
}
static inline Time_t operator +(
const Time_t& ta,
const Time_t& tb)
{
Time_t result(ta.seconds() + tb.seconds(), ta.fraction() + tb.fraction());
if (result.fraction() < ta.fraction()) // Overflow is detected by any of them
{
++result.seconds();
}
return result;
}
static inline Time_t operator -(
const Time_t& ta,
const Time_t& tb)
{
Time_t result(ta.seconds() - tb.seconds(), ta.fraction() - tb.fraction());
if (result.fraction() > ta.fraction()) // Overflow is detected by ta
{
--result.seconds();
}
return result;
}
#endif // ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
const Time_t c_RTPSTimeInfinite{0x7fffffff, 0xffffffff};
const Time_t c_RTPSTimeZero{0, 0};
const Time_t c_RTPSTimeInvalid{-1, 0xffffffff};
} // namespace rtps
#ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
static inline bool operator ==(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds != t2.seconds)
{
return false;
}
if (t1.nanosec != t2.nanosec)
{
return false;
}
return true;
}
static inline bool operator !=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds != t2.seconds)
{
return true;
}
if (t1.nanosec != t2.nanosec)
{
return true;
}
return false;
}
static inline bool operator <(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds < t2.seconds)
{
return true;
}
else if (t1.seconds > t2.seconds)
{
return false;
}
else
{
if (t1.nanosec < t2.nanosec)
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator >(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds > t2.seconds)
{
return true;
}
else if (t1.seconds < t2.seconds)
{
return false;
}
else
{
if (t1.nanosec > t2.nanosec)
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator <=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds < t2.seconds)
{
return true;
}
else if (t1.seconds > t2.seconds)
{
return false;
}
else
{
if (t1.nanosec <= t2.nanosec)
{
return true;
}
else
{
return false;
}
}
}
static inline bool operator >=(
const Time_t& t1,
const Time_t& t2)
{
if (t1.seconds > t2.seconds)
{
return true;
}
else if (t1.seconds < t2.seconds)
{
return false;
}
else
{
if (t1.nanosec >= t2.nanosec)
{
return true;
}
else
{
return false;
}
}
}
inline std::ostream& operator <<(
std::ostream& output,
const Time_t& t)
{
long double t_aux = t.seconds + (((long double)t.nanosec) / 1000000000ULL);
return output << t_aux;
}
static inline Time_t operator +(
const Time_t& ta,
const Time_t& tb)
{
Time_t result(ta.seconds + tb.seconds, ta.nanosec + tb.nanosec);
if (result.nanosec < ta.nanosec) // Overflow is detected by any of them
{
++result.seconds;
}
return result;
}
static inline Time_t operator -(
const Time_t& ta,
const Time_t& tb)
{
Time_t result(ta.seconds - tb.seconds, ta.nanosec - tb.nanosec);
if (result.nanosec > ta.nanosec) // Overflow is detected by ta
{
--result.seconds;
}
return result;
}
#endif // ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
const Time_t c_TimeInfinite{Time_t::INFINITE_SECONDS, Time_t::INFINITE_NANOSECONDS};
const Time_t c_TimeZero{0, 0};
const Time_t c_TimeInvalid{-1, Time_t::INFINITE_NANOSECONDS};
} // namespace fastrtps
} // namespace eprosima
// defines to avoid the "static initialization order fiasco"
#define TIME_T_INFINITE_SECONDS (eprosima::fastrtps::Time_t::INFINITE_SECONDS)
#define TIME_T_INFINITE_NANOSECONDS (eprosima::fastrtps::Time_t::INFINITE_NANOSECONDS)
#endif /* _FASTDDS_RTPS_TIME_T_H_ */