1// Copyright (c) 2019-2020 Alexander Medvednikov. All rights reserved. 2// Use of this source code is governed by an MIT license 3// that can be found in the LICENSE file. 4module time 5 6#include <time.h> 7 8struct C.tm { 9 tm_sec int 10 tm_min int 11 tm_hour int 12 tm_mday int 13 tm_mon int 14 tm_year int 15 tm_wday int 16 tm_yday int 17 tm_isdst int 18} 19 20fn C.timegm(&tm) time_t 21fn C.localtime_r(t &C.time_t, tm &C.tm ) 22 23fn make_unix_time(t C.tm) int { 24 return int(C.timegm(&t)) 25} 26 27fn to_local_time(t Time) Time { 28 loc_tm := C.tm{} 29 C.localtime_r(time_t(&t.unix), &loc_tm) 30 31 return convert_ctime(loc_tm, t.microsecond) 32} 33 34type time_t voidptr 35 36// in most systems, these are __quad_t, which is an i64 37struct C.timespec { 38mut: 39 tv_sec i64 40 tv_nsec i64 41} 42 43// the first arg is defined in include/bits/types.h as `__S32_TYPE`, which is `int` 44fn C.clock_gettime(int, &C.timespec) 45 46pub fn sys_mono_now() u64 { 47 $if macos { 48 return sys_mono_now_darwin() 49 } $else { 50 ts := C.timespec{} 51 C.clock_gettime(C.CLOCK_MONOTONIC, &ts) 52 return u64(ts.tv_sec) * 1_000_000_000 + u64(ts.tv_nsec) 53 } 54} 55 56// NB: vpc_now is used by `v -profile` . 57// It should NOT call *any other v function*, just C functions and casts. 58[inline] 59fn vpc_now() u64 { 60 ts := C.timespec{} 61 C.clock_gettime(C.CLOCK_MONOTONIC, &ts) 62 return u64(ts.tv_sec) * 1_000_000_000 + u64(ts.tv_nsec) 63} 64 65 66 67// dummy to compile with all compilers 68pub fn win_now() Time { 69 return Time{} 70} 71 72// dummy to compile with all compilers 73pub fn win_utc() Time { 74 return Time{} 75} 76 77// dummy to compile with all compilers 78pub struct C.timeval { 79 tv_sec u64 80 tv_usec u64 81} 82 83// return absolute timespec for now()+d 84pub fn (d Duration) timespec() C.timespec { 85 mut ts := C.timespec{} 86 C.clock_gettime(C.CLOCK_REALTIME, &ts) 87 d_sec := d / second 88 d_nsec := d % second 89 ts.tv_sec += d_sec 90 ts.tv_nsec += d_nsec 91 if ts.tv_nsec > second { 92 ts.tv_nsec -= second 93 ts.tv_sec++ 94 } 95 return ts 96} 97 98// return timespec of 1970/1/1 99pub fn zero_timespec() C.timespec { 100 ts := C.timespec{ 101 tv_sec: 0 102 tv_nsec: 0 103 } 104 return ts 105} 106