Time_t.h 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629
  1. // Copyright 2019 Proyectos y Sistemas de Mantenimiento SL (eProsima).
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. /**
  15. * @file Time_t.h
  16. */
  17. #ifndef _FASTDDS_RTPS_TIME_T_H_
  18. #define _FASTDDS_RTPS_TIME_T_H_
  19. #include <fastrtps/fastrtps_dll.h>
  20. #include <cmath>
  21. #include <cstdint>
  22. #include <iostream>
  23. // defines to avoid the "static initialization order fiasco"
  24. #define TIME_T_INFINITE_SECONDS 0x7fffffff
  25. #define TIME_T_INFINITE_NANOSECONDS 0xffffffff
  26. namespace eprosima {
  27. namespace fastrtps {
  28. /**
  29. * Structure Time_t, used to describe times.
  30. * @ingroup COMMON_MODULE
  31. */
  32. struct RTPS_DllAPI Time_t
  33. {
  34. int32_t seconds;
  35. uint32_t nanosec;
  36. //! Default constructor. Sets values to zero.
  37. Time_t();
  38. /**
  39. * @param sec Seconds
  40. * @param nsec Nanoseconds
  41. */
  42. Time_t(
  43. int32_t sec,
  44. uint32_t nsec);
  45. /**
  46. * @param sec Seconds. The fractional part is converted to nanoseconds.
  47. */
  48. Time_t(
  49. long double sec);
  50. void fraction(
  51. uint32_t frac);
  52. uint32_t fraction() const;
  53. /**
  54. * Returns stored time as nanoseconds (including seconds)
  55. */
  56. int64_t to_ns() const;
  57. /**
  58. * Fills a Time_t struct with a representation of the current time.
  59. *
  60. * @param ret Reference to the structure to be filled in.
  61. */
  62. static void now(
  63. Time_t& ret);
  64. };
  65. using Duration_t = Time_t;
  66. namespace rtps {
  67. /**
  68. * Structure Time_t, used to describe times at RTPS protocol.
  69. * @ingroup COMMON_MODULE
  70. */
  71. class RTPS_DllAPI Time_t
  72. {
  73. public:
  74. //! Default constructor. Sets values to zero.
  75. Time_t();
  76. /**
  77. * @param sec Seconds
  78. * @param frac Fraction of second
  79. */
  80. Time_t(
  81. int32_t sec,
  82. uint32_t frac);
  83. /**
  84. * @param sec Seconds. The fractional part is converted to nanoseconds.
  85. */
  86. Time_t(
  87. long double sec);
  88. /**
  89. * @param time fastrtps::Time_t, aka. Duration_t.
  90. */
  91. Time_t(
  92. const eprosima::fastrtps::Time_t& time);
  93. /**
  94. * Returns stored time as nanoseconds (including seconds)
  95. */
  96. int64_t to_ns() const;
  97. /**
  98. * Retrieve the seconds field.
  99. */
  100. int32_t seconds() const;
  101. /**
  102. * Retrieve the seconds field by ref.
  103. */
  104. int32_t& seconds();
  105. /**
  106. * Sets seconds field.
  107. */
  108. void seconds(
  109. int32_t sec);
  110. /**
  111. * Retrieve the nanosec field.
  112. */
  113. uint32_t nanosec() const;
  114. /**
  115. * Sets nanoseconds field and updates the fraction.
  116. */
  117. void nanosec(
  118. uint32_t nanos);
  119. /**
  120. * Retrieve the fraction field.
  121. */
  122. uint32_t fraction() const;
  123. /**
  124. * Sets fraction field and updates the nanoseconds.
  125. */
  126. void fraction(
  127. uint32_t frac);
  128. Duration_t to_duration_t() const;
  129. void from_duration_t(const Duration_t& duration);
  130. /**
  131. * Fills a Time_t struct with a representation of the current time.
  132. *
  133. * @param ret Reference to the structure to be filled in.
  134. */
  135. static void now(
  136. Time_t& ret);
  137. private:
  138. //!Seconds
  139. int32_t seconds_;
  140. //!Fraction of second (1 fraction = 1/(2^32) seconds)
  141. uint32_t fraction_;
  142. //!Nanoseconds
  143. uint32_t nanosec_;
  144. void set_fraction(
  145. uint32_t frac);
  146. void set_nanosec(
  147. uint32_t nanos);
  148. };
  149. #ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
  150. /**
  151. * Comparison assignment
  152. * @param t1 First Time_t to compare
  153. * @param t2 Second Time_t to compare
  154. * @return True if equal
  155. */
  156. static inline bool operator==(
  157. const Time_t& t1,
  158. const Time_t& t2)
  159. {
  160. if(t1.seconds() != t2.seconds())
  161. {
  162. return false;
  163. }
  164. if(t1.fraction() != t2.fraction())
  165. {
  166. return false;
  167. }
  168. return true;
  169. }
  170. /**
  171. * Comparison assignment
  172. * @param t1 First Time_t to compare
  173. * @param t2 Second Time_t to compare
  174. * @return True if not equal
  175. */
  176. static inline bool operator!=(
  177. const Time_t& t1,
  178. const Time_t& t2)
  179. {
  180. if (t1.seconds() != t2.seconds())
  181. {
  182. return true;
  183. }
  184. if (t1.fraction() != t2.fraction())
  185. {
  186. return true;
  187. }
  188. return false;
  189. }
  190. /**
  191. * Checks if a Time_t is less than other.
  192. * @param t1 First Time_t to compare
  193. * @param t2 Second Time_t to compare
  194. * @return True if the first Time_t is less than the second
  195. */
  196. static inline bool operator<(
  197. const Time_t& t1,
  198. const Time_t& t2)
  199. {
  200. if (t1.seconds() < t2.seconds())
  201. {
  202. return true;
  203. }
  204. else if (t1.seconds() > t2.seconds())
  205. {
  206. return false;
  207. }
  208. else
  209. {
  210. if (t1.fraction() < t2.fraction())
  211. {
  212. return true;
  213. }
  214. else
  215. {
  216. return false;
  217. }
  218. }
  219. }
  220. /**
  221. * Checks if a Time_t is greather than other.
  222. * @param t1 First Time_t to compare
  223. * @param t2 Second Time_t to compare
  224. * @return True if the first Time_t is greather than the second
  225. */
  226. static inline bool operator>(
  227. const Time_t& t1,
  228. const Time_t& t2)
  229. {
  230. if (t1.seconds() > t2.seconds())
  231. {
  232. return true;
  233. }
  234. else if (t1.seconds() < t2.seconds())
  235. {
  236. return false;
  237. }
  238. else
  239. {
  240. if (t1.fraction() > t2.fraction())
  241. {
  242. return true;
  243. }
  244. else
  245. {
  246. return false;
  247. }
  248. }
  249. }
  250. /**
  251. * Checks if a Time_t is less or equal than other.
  252. * @param t1 First Time_t to compare
  253. * @param t2 Second Time_t to compare
  254. * @return True if the first Time_t is less or equal than the second
  255. */
  256. static inline bool operator<=(
  257. const Time_t& t1,
  258. const Time_t& t2)
  259. {
  260. if (t1.seconds() < t2.seconds())
  261. {
  262. return true;
  263. }
  264. else if (t1.seconds() > t2.seconds())
  265. {
  266. return false;
  267. }
  268. else
  269. {
  270. if (t1.fraction() <= t2.fraction())
  271. {
  272. return true;
  273. }
  274. else
  275. {
  276. return false;
  277. }
  278. }
  279. }
  280. /**
  281. * Checks if a Time_t is greather or equal than other.
  282. * @param t1 First Time_t to compare
  283. * @param t2 Second Time_t to compare
  284. * @return True if the first Time_t is greather or equal than the second
  285. */
  286. static inline bool operator>=(
  287. const Time_t& t1,
  288. const Time_t& t2)
  289. {
  290. if (t1.seconds() > t2.seconds())
  291. {
  292. return true;
  293. }
  294. else if (t1.seconds() < t2.seconds())
  295. {
  296. return false;
  297. }
  298. else
  299. {
  300. if (t1.fraction() >= t2.fraction())
  301. {
  302. return true;
  303. }
  304. else
  305. {
  306. return false;
  307. }
  308. }
  309. }
  310. inline std::ostream& operator<<(
  311. std::ostream& output,
  312. const Time_t& t)
  313. {
  314. long double t_aux = t.seconds() + (((long double)t.nanosec()) / 1000000000ULL);
  315. return output << t_aux;
  316. }
  317. /**
  318. * Adds two Time_t.
  319. * @param ta First Time_t to add
  320. * @param tb Second Time_t to add
  321. * @return A new Time_t with the result.
  322. */
  323. static inline Time_t operator+(
  324. const Time_t &ta,
  325. const Time_t &tb)
  326. {
  327. Time_t result(ta.seconds() + tb.seconds(), ta.fraction() + tb.fraction());
  328. if (result.fraction() < ta.fraction()) // Overflow is detected by any of them
  329. {
  330. ++result.seconds();
  331. }
  332. return result;
  333. }
  334. /**
  335. * Substracts two Time_t.
  336. * @param ta First Time_t to substract
  337. * @param tb Second Time_t to substract
  338. * @return A new Time_t with the result.
  339. */
  340. static inline Time_t operator-(
  341. const Time_t &ta,
  342. const Time_t &tb)
  343. {
  344. Time_t result(ta.seconds() - tb.seconds(), ta.fraction() - tb.fraction());
  345. if (result.fraction() > ta.fraction()) // Overflow is detected by ta
  346. {
  347. --result.seconds();
  348. }
  349. return result;
  350. }
  351. #endif
  352. const Time_t c_RTPSTimeInfinite(0x7fffffff,0xffffffff);
  353. const Time_t c_RTPSTimeZero(0,0);
  354. const Time_t c_RTPSTimeInvalid(-1,0xffffffff);
  355. } // namespace rtps
  356. #ifndef DOXYGEN_SHOULD_SKIP_THIS_PUBLIC
  357. /**
  358. * Comparison assignment
  359. * @param t1 First Time_t to compare
  360. * @param t2 Second Time_t to compare
  361. * @return True if equal
  362. */
  363. static inline bool operator==(
  364. const Time_t& t1,
  365. const Time_t& t2)
  366. {
  367. if(t1.seconds != t2.seconds)
  368. {
  369. return false;
  370. }
  371. if(t1.nanosec != t2.nanosec)
  372. {
  373. return false;
  374. }
  375. return true;
  376. }
  377. /**
  378. * Comparison assignment
  379. * @param t1 First Time_t to compare
  380. * @param t2 Second Time_t to compare
  381. * @return True if not equal
  382. */
  383. static inline bool operator!=(
  384. const Time_t& t1,
  385. const Time_t& t2)
  386. {
  387. if (t1.seconds != t2.seconds)
  388. {
  389. return true;
  390. }
  391. if (t1.nanosec != t2.nanosec)
  392. {
  393. return true;
  394. }
  395. return false;
  396. }
  397. /**
  398. * Checks if a Time_t is less than other.
  399. * @param t1 First Time_t to compare
  400. * @param t2 Second Time_t to compare
  401. * @return True if the first Time_t is less than the second
  402. */
  403. static inline bool operator<(
  404. const Time_t& t1,
  405. const Time_t& t2)
  406. {
  407. if (t1.seconds < t2.seconds)
  408. {
  409. return true;
  410. }
  411. else if (t1.seconds > t2.seconds)
  412. {
  413. return false;
  414. }
  415. else
  416. {
  417. if (t1.nanosec < t2.nanosec)
  418. {
  419. return true;
  420. }
  421. else
  422. {
  423. return false;
  424. }
  425. }
  426. }
  427. /**
  428. * Checks if a Time_t is greather than other.
  429. * @param t1 First Time_t to compare
  430. * @param t2 Second Time_t to compare
  431. * @return True if the first Time_t is greather than the second
  432. */
  433. static inline bool operator>(
  434. const Time_t& t1,
  435. const Time_t& t2)
  436. {
  437. if (t1.seconds > t2.seconds)
  438. {
  439. return true;
  440. }
  441. else if (t1.seconds < t2.seconds)
  442. {
  443. return false;
  444. }
  445. else
  446. {
  447. if (t1.nanosec > t2.nanosec)
  448. {
  449. return true;
  450. }
  451. else
  452. {
  453. return false;
  454. }
  455. }
  456. }
  457. /**
  458. * Checks if a Time_t is less or equal than other.
  459. * @param t1 First Time_t to compare
  460. * @param t2 Second Time_t to compare
  461. * @return True if the first Time_t is less or equal than the second
  462. */
  463. static inline bool operator<=(
  464. const Time_t& t1,
  465. const Time_t& t2)
  466. {
  467. if (t1.seconds < t2.seconds)
  468. {
  469. return true;
  470. }
  471. else if (t1.seconds > t2.seconds)
  472. {
  473. return false;
  474. }
  475. else
  476. {
  477. if (t1.nanosec <= t2.nanosec)
  478. {
  479. return true;
  480. }
  481. else
  482. {
  483. return false;
  484. }
  485. }
  486. }
  487. /**
  488. * Checks if a Time_t is greather or equal than other.
  489. * @param t1 First Time_t to compare
  490. * @param t2 Second Time_t to compare
  491. * @return True if the first Time_t is greather or equal than the second
  492. */
  493. static inline bool operator>=(
  494. const Time_t& t1,
  495. const Time_t& t2)
  496. {
  497. if (t1.seconds > t2.seconds)
  498. {
  499. return true;
  500. }
  501. else if (t1.seconds < t2.seconds)
  502. {
  503. return false;
  504. }
  505. else
  506. {
  507. if (t1.nanosec >= t2.nanosec)
  508. {
  509. return true;
  510. }
  511. else
  512. {
  513. return false;
  514. }
  515. }
  516. }
  517. inline std::ostream& operator<<(
  518. std::ostream& output,
  519. const Time_t& t)
  520. {
  521. long double t_aux = t.seconds + (((long double)t.nanosec) / 1000000000ULL);
  522. return output << t_aux;
  523. }
  524. /**
  525. * Adds two Time_t.
  526. * @param ta First Time_t to add
  527. * @param tb Second Time_t to add
  528. * @return A new Time_t with the result.
  529. */
  530. static inline Time_t operator+(
  531. const Time_t &ta,
  532. const Time_t &tb)
  533. {
  534. Time_t result(ta.seconds + tb.seconds, ta.nanosec + tb.nanosec);
  535. if (result.nanosec < ta.nanosec) // Overflow is detected by any of them
  536. {
  537. ++result.seconds;
  538. }
  539. return result;
  540. }
  541. /**
  542. * Substracts two Time_t.
  543. * @param ta First Time_t to substract
  544. * @param tb Second Time_t to substract
  545. * @return A new Time_t with the result.
  546. */
  547. static inline Time_t operator-(
  548. const Time_t &ta,
  549. const Time_t &tb)
  550. {
  551. Time_t result(ta.seconds - tb.seconds, ta.nanosec - tb.nanosec);
  552. if (result.nanosec > ta.nanosec) // Overflow is detected by ta
  553. {
  554. --result.seconds;
  555. }
  556. return result;
  557. }
  558. #endif
  559. //! Time_t (Duration_t) representing an infinite time. DONT USE IT IN CONSTRUCTORS
  560. const Time_t c_TimeInfinite(TIME_T_INFINITE_SECONDS, TIME_T_INFINITE_NANOSECONDS);
  561. //! Time_t (Duration_t) representing a zero time. DONT USE IT IN CONSTRUCTORS
  562. const Time_t c_TimeZero(0,0);
  563. //! Time_t (Duration_t) representing an invalid time. DONT USE IT IN CONSTRUCTORS
  564. const Time_t c_TimeInvalid(-1, TIME_T_INFINITE_NANOSECONDS);
  565. } // namespace fastrtps
  566. } // namespace eprosima
  567. #endif /* _FASTDDS_RTPS_TIME_T_H_ */