aboutsummaryrefslogtreecommitdiff
path: root/src/util/time.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/util/time.c')
-rw-r--r--src/util/time.c218
1 files changed, 191 insertions, 27 deletions
diff --git a/src/util/time.c b/src/util/time.c
index 144e1b401..83b39b4e8 100644
--- a/src/util/time.c
+++ b/src/util/time.c
@@ -58,27 +58,35 @@ GNUNET_TIME_get_offset ()
58} 58}
59 59
60 60
61int 61struct GNUNET_TIME_Timestamp
62GNUNET_TIME_round_abs (struct GNUNET_TIME_Absolute *at) 62GNUNET_TIME_absolute_to_timestamp (struct GNUNET_TIME_Absolute at)
63{ 63{
64 if (at->abs_value_us == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value_us) 64 struct GNUNET_TIME_Timestamp ts;
65 return GNUNET_OK; 65
66 if (0 == at->abs_value_us % 1000000) 66 if (GNUNET_TIME_absolute_is_never (at))
67 return GNUNET_OK; 67 return GNUNET_TIME_UNIT_FOREVER_TS;
68 at->abs_value_us -= at->abs_value_us % 1000000; 68 ts.abs_time.abs_value_us = at.abs_value_us - at.abs_value_us % 1000000;
69 return GNUNET_NO; 69 return ts;
70}
71
72
73struct GNUNET_TIME_TimestampNBO
74GNUNET_TIME_timestamp_hton (struct GNUNET_TIME_Timestamp t)
75{
76 struct GNUNET_TIME_TimestampNBO tn;
77
78 tn.abs_time_nbo = GNUNET_TIME_absolute_hton (t.abs_time);
79 return tn;
70} 80}
71 81
72 82
73int 83struct GNUNET_TIME_Timestamp
74GNUNET_TIME_round_rel (struct GNUNET_TIME_Relative *rt) 84GNUNET_TIME_timestamp_ntoh (struct GNUNET_TIME_TimestampNBO tn)
75{ 85{
76 if (rt->rel_value_us == GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us) 86 struct GNUNET_TIME_Timestamp t;
77 return GNUNET_OK; 87
78 if (0 == rt->rel_value_us % 1000000) 88 t.abs_time = GNUNET_TIME_absolute_ntoh (tn.abs_time_nbo);
79 return GNUNET_OK; 89 return t;
80 rt->rel_value_us -= rt->rel_value_us % 1000000;
81 return GNUNET_NO;
82} 90}
83 91
84 92
@@ -96,6 +104,14 @@ GNUNET_TIME_absolute_get ()
96} 104}
97 105
98 106
107struct GNUNET_TIME_Timestamp
108GNUNET_TIME_timestamp_get ()
109{
110 return GNUNET_TIME_absolute_to_timestamp (
111 GNUNET_TIME_absolute_get ());
112}
113
114
99struct GNUNET_TIME_Relative 115struct GNUNET_TIME_Relative
100GNUNET_TIME_relative_get_zero_ () 116GNUNET_TIME_relative_get_zero_ ()
101{ 117{
@@ -177,12 +193,114 @@ GNUNET_TIME_absolute_get_forever_ ()
177} 193}
178 194
179 195
196const char *
197GNUNET_TIME_timestamp2s (struct GNUNET_TIME_Timestamp ts)
198{
199 static GNUNET_THREAD_LOCAL char buf[255];
200 time_t tt;
201 struct tm *tp;
202
203 if (GNUNET_TIME_absolute_is_never (ts.abs_time))
204 return "end of time";
205 tt = ts.abs_time.abs_value_us / 1000LL / 1000LL;
206 tp = localtime (&tt);
207 /* This is hacky, but i don't know a way to detect libc character encoding.
208 * Just expect utf8 from glibc these days.
209 * As for msvcrt, use the wide variant, which always returns utf16
210 * (otherwise we'd have to detect current codepage or use W32API character
211 * set conversion routines to convert to UTF8).
212 */
213 strftime (buf,
214 sizeof(buf),
215 "%a %b %d %H:%M:%S %Y",
216 tp);
217 return buf;
218}
219
220
221const char *
222GNUNET_TIME_absolute2s (struct GNUNET_TIME_Absolute t)
223{
224 static GNUNET_THREAD_LOCAL char buf[255];
225 time_t tt;
226 struct tm *tp;
227
228 if (GNUNET_TIME_absolute_is_never (t))
229 return "end of time";
230 tt = t.abs_value_us / 1000LL / 1000LL;
231 tp = localtime (&tt);
232 /* This is hacky, but i don't know a way to detect libc character encoding.
233 * Just expect utf8 from glibc these days.
234 * As for msvcrt, use the wide variant, which always returns utf16
235 * (otherwise we'd have to detect current codepage or use W32API character
236 * set conversion routines to convert to UTF8).
237 */
238 strftime (buf,
239 sizeof(buf),
240 "%a %b %d %H:%M:%S %Y",
241 tp);
242 return buf;
243}
244
245
246const char *
247GNUNET_TIME_relative2s (struct GNUNET_TIME_Relative delta,
248 bool do_round)
249{
250 static GNUNET_THREAD_LOCAL char buf[128];
251 const char *unit = /* time unit */ "µs";
252 uint64_t dval = delta.rel_value_us;
253
254 if (GNUNET_TIME_relative_is_forever (delta))
255 return "forever";
256 if (0 == delta.rel_value_us)
257 return "0 ms";
258 if ( ((GNUNET_YES == do_round) &&
259 (dval > 5 * 1000)) ||
260 (0 == (dval % 1000)))
261 {
262 dval = dval / 1000;
263 unit = /* time unit */ "ms";
264 if (((GNUNET_YES == do_round) && (dval > 5 * 1000)) || (0 == (dval % 1000)))
265 {
266 dval = dval / 1000;
267 unit = /* time unit */ "s";
268 if (((GNUNET_YES == do_round) && (dval > 5 * 60)) || (0 == (dval % 60)))
269 {
270 dval = dval / 60;
271 unit = /* time unit */ "m";
272 if (((GNUNET_YES == do_round) && (dval > 5 * 60)) || (0 == (dval % 60)))
273 {
274 dval = dval / 60;
275 unit = /* time unit */ "h";
276 if (((GNUNET_YES == do_round) && (dval > 5 * 24)) ||
277 (0 == (dval % 24)))
278 {
279 dval = dval / 24;
280 if (1 == dval)
281 unit = /* time unit */ "day";
282 else
283 unit = /* time unit */ "days";
284 }
285 }
286 }
287 }
288 }
289 GNUNET_snprintf (buf,
290 sizeof(buf),
291 "%llu %s",
292 (unsigned long long) dval,
293 unit);
294 return buf;
295}
296
297
180struct GNUNET_TIME_Absolute 298struct GNUNET_TIME_Absolute
181GNUNET_TIME_relative_to_absolute (struct GNUNET_TIME_Relative rel) 299GNUNET_TIME_relative_to_absolute (struct GNUNET_TIME_Relative rel)
182{ 300{
183 struct GNUNET_TIME_Absolute ret; 301 struct GNUNET_TIME_Absolute ret;
184 302
185 if (rel.rel_value_us == UINT64_MAX) 303 if (GNUNET_TIME_relative_is_forever (rel))
186 return GNUNET_TIME_UNIT_FOREVER_ABS; 304 return GNUNET_TIME_UNIT_FOREVER_ABS;
187 struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get (); 305 struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get ();
188 306
@@ -196,6 +314,14 @@ GNUNET_TIME_relative_to_absolute (struct GNUNET_TIME_Relative rel)
196} 314}
197 315
198 316
317struct GNUNET_TIME_Timestamp
318GNUNET_TIME_relative_to_timestamp (struct GNUNET_TIME_Relative rel)
319{
320 return GNUNET_TIME_absolute_to_timestamp (
321 GNUNET_TIME_relative_to_absolute (rel));
322}
323
324
199struct GNUNET_TIME_Relative 325struct GNUNET_TIME_Relative
200GNUNET_TIME_relative_min (struct GNUNET_TIME_Relative t1, 326GNUNET_TIME_relative_min (struct GNUNET_TIME_Relative t1,
201 struct GNUNET_TIME_Relative t2) 327 struct GNUNET_TIME_Relative t2)
@@ -228,12 +354,28 @@ GNUNET_TIME_absolute_max (struct GNUNET_TIME_Absolute t1,
228} 354}
229 355
230 356
357struct GNUNET_TIME_Timestamp
358GNUNET_TIME_timestamp_max (struct GNUNET_TIME_Timestamp t1,
359 struct GNUNET_TIME_Timestamp t2)
360{
361 return (t1.abs_time.abs_value_us > t2.abs_time.abs_value_us) ? t1 : t2;
362}
363
364
365struct GNUNET_TIME_Timestamp
366GNUNET_TIME_timestamp_min (struct GNUNET_TIME_Timestamp t1,
367 struct GNUNET_TIME_Timestamp t2)
368{
369 return (t1.abs_time.abs_value_us < t2.abs_time.abs_value_us) ? t1 : t2;
370}
371
372
231struct GNUNET_TIME_Relative 373struct GNUNET_TIME_Relative
232GNUNET_TIME_absolute_get_remaining (struct GNUNET_TIME_Absolute future) 374GNUNET_TIME_absolute_get_remaining (struct GNUNET_TIME_Absolute future)
233{ 375{
234 struct GNUNET_TIME_Relative ret; 376 struct GNUNET_TIME_Relative ret;
235 377
236 if (future.abs_value_us == UINT64_MAX) 378 if (GNUNET_TIME_absolute_is_never (future))
237 return GNUNET_TIME_UNIT_FOREVER_REL; 379 return GNUNET_TIME_UNIT_FOREVER_REL;
238 struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get (); 380 struct GNUNET_TIME_Absolute now = GNUNET_TIME_absolute_get ();
239 381
@@ -250,7 +392,7 @@ GNUNET_TIME_absolute_get_difference (struct GNUNET_TIME_Absolute start,
250{ 392{
251 struct GNUNET_TIME_Relative ret; 393 struct GNUNET_TIME_Relative ret;
252 394
253 if (end.abs_value_us == UINT64_MAX) 395 if (GNUNET_TIME_absolute_is_never (end))
254 return GNUNET_TIME_UNIT_FOREVER_REL; 396 return GNUNET_TIME_UNIT_FOREVER_REL;
255 if (end.abs_value_us < start.abs_value_us) 397 if (end.abs_value_us < start.abs_value_us)
256 return GNUNET_TIME_UNIT_ZERO; 398 return GNUNET_TIME_UNIT_ZERO;
@@ -279,8 +421,8 @@ GNUNET_TIME_absolute_add (struct GNUNET_TIME_Absolute start,
279{ 421{
280 struct GNUNET_TIME_Absolute ret; 422 struct GNUNET_TIME_Absolute ret;
281 423
282 if ((start.abs_value_us == UINT64_MAX) || 424 if (GNUNET_TIME_absolute_is_never (start) ||
283 (duration.rel_value_us == UINT64_MAX)) 425 GNUNET_TIME_relative_is_forever (duration))
284 return GNUNET_TIME_UNIT_FOREVER_ABS; 426 return GNUNET_TIME_UNIT_FOREVER_ABS;
285 if (start.abs_value_us + duration.rel_value_us < start.abs_value_us) 427 if (start.abs_value_us + duration.rel_value_us < start.abs_value_us)
286 { 428 {
@@ -300,7 +442,7 @@ GNUNET_TIME_absolute_subtract (struct GNUNET_TIME_Absolute start,
300 442
301 if (start.abs_value_us <= duration.rel_value_us) 443 if (start.abs_value_us <= duration.rel_value_us)
302 return GNUNET_TIME_UNIT_ZERO_ABS; 444 return GNUNET_TIME_UNIT_ZERO_ABS;
303 if (start.abs_value_us == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value_us) 445 if (GNUNET_TIME_absolute_is_never (start))
304 return GNUNET_TIME_UNIT_FOREVER_ABS; 446 return GNUNET_TIME_UNIT_FOREVER_ABS;
305 ret.abs_value_us = start.abs_value_us - duration.rel_value_us; 447 ret.abs_value_us = start.abs_value_us - duration.rel_value_us;
306 return ret; 448 return ret;
@@ -315,7 +457,7 @@ GNUNET_TIME_relative_multiply (struct GNUNET_TIME_Relative rel,
315 457
316 if (0 == factor) 458 if (0 == factor)
317 return GNUNET_TIME_UNIT_ZERO; 459 return GNUNET_TIME_UNIT_ZERO;
318 if (rel.rel_value_us == GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us) 460 if (GNUNET_TIME_relative_is_forever (rel))
319 return GNUNET_TIME_UNIT_FOREVER_REL; 461 return GNUNET_TIME_UNIT_FOREVER_REL;
320 ret.rel_value_us = rel.rel_value_us * factor; 462 ret.rel_value_us = rel.rel_value_us * factor;
321 if (ret.rel_value_us / factor != rel.rel_value_us) 463 if (ret.rel_value_us / factor != rel.rel_value_us)
@@ -328,7 +470,8 @@ GNUNET_TIME_relative_multiply (struct GNUNET_TIME_Relative rel,
328 470
329 471
330struct GNUNET_TIME_Relative 472struct GNUNET_TIME_Relative
331relative_multiply_double (struct GNUNET_TIME_Relative rel, double factor) 473relative_multiply_double (struct GNUNET_TIME_Relative rel,
474 double factor)
332{ 475{
333 struct GNUNET_TIME_Relative out; 476 struct GNUNET_TIME_Relative out;
334 double m; 477 double m;
@@ -337,7 +480,7 @@ relative_multiply_double (struct GNUNET_TIME_Relative rel, double factor)
337 480
338 if (0 == factor) 481 if (0 == factor)
339 return GNUNET_TIME_UNIT_ZERO; 482 return GNUNET_TIME_UNIT_ZERO;
340 if (rel.rel_value_us == GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us) 483 if (GNUNET_TIME_relative_is_forever (rel))
341 return GNUNET_TIME_UNIT_FOREVER_REL; 484 return GNUNET_TIME_UNIT_FOREVER_REL;
342 485
343 m = ((double) rel.rel_value_us) * factor; 486 m = ((double) rel.rel_value_us) * factor;
@@ -361,7 +504,7 @@ GNUNET_TIME_relative_saturating_multiply (struct GNUNET_TIME_Relative rel,
361 504
362 if (0 == factor) 505 if (0 == factor)
363 return GNUNET_TIME_UNIT_ZERO; 506 return GNUNET_TIME_UNIT_ZERO;
364 if (rel.rel_value_us == GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us) 507 if (GNUNET_TIME_relative_is_forever (rel))
365 return GNUNET_TIME_UNIT_FOREVER_REL; 508 return GNUNET_TIME_UNIT_FOREVER_REL;
366 ret.rel_value_us = rel.rel_value_us * factor; 509 ret.rel_value_us = rel.rel_value_us * factor;
367 if (ret.rel_value_us / factor != rel.rel_value_us) 510 if (ret.rel_value_us / factor != rel.rel_value_us)
@@ -379,7 +522,7 @@ GNUNET_TIME_relative_divide (struct GNUNET_TIME_Relative rel,
379 struct GNUNET_TIME_Relative ret; 522 struct GNUNET_TIME_Relative ret;
380 523
381 if ((0 == factor) || 524 if ((0 == factor) ||
382 (rel.rel_value_us == GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us)) 525 (GNUNET_TIME_relative_is_forever (rel)))
383 return GNUNET_TIME_UNIT_FOREVER_REL; 526 return GNUNET_TIME_UNIT_FOREVER_REL;
384 ret.rel_value_us = rel.rel_value_us / factor; 527 ret.rel_value_us = rel.rel_value_us / factor;
385 return ret; 528 return ret;
@@ -538,6 +681,20 @@ GNUNET_TIME_absolute_from_s (uint64_t s_after_epoch)
538} 681}
539 682
540 683
684struct GNUNET_TIME_Timestamp
685GNUNET_TIME_timestamp_from_s (uint64_t s_after_epoch)
686{
687 struct GNUNET_TIME_Timestamp ret;
688
689 ret.abs_time.abs_value_us
690 = GNUNET_TIME_UNIT_SECONDS.rel_value_us * s_after_epoch;
691 if (ret.abs_time.abs_value_us / GNUNET_TIME_UNIT_SECONDS.rel_value_us
692 != s_after_epoch)
693 ret = GNUNET_TIME_UNIT_FOREVER_TS;
694 return ret;
695}
696
697
541struct GNUNET_TIME_Absolute 698struct GNUNET_TIME_Absolute
542GNUNET_TIME_absolute_ntoh (struct GNUNET_TIME_AbsoluteNBO a) 699GNUNET_TIME_absolute_ntoh (struct GNUNET_TIME_AbsoluteNBO a)
543{ 700{
@@ -645,6 +802,13 @@ GNUNET_TIME_randomized_backoff (struct GNUNET_TIME_Relative rt,
645} 802}
646 803
647 804
805bool
806GNUNET_TIME_absolute_is_zero (struct GNUNET_TIME_Absolute abs)
807{
808 return 0 == abs.abs_value_us;
809}
810
811
648struct GNUNET_TIME_Relative 812struct GNUNET_TIME_Relative
649GNUNET_TIME_randomize (struct GNUNET_TIME_Relative r) 813GNUNET_TIME_randomize (struct GNUNET_TIME_Relative r)
650{ 814{