forked from kmarkus/rFSM
-
Notifications
You must be signed in to change notification settings - Fork 0
/
time.lua
118 lines (102 loc) · 2.68 KB
/
time.lua
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
--- Various sys/time.h like operations.
-- Take struct timespec tables with 'sec' and 'nsec' fields as input
-- and return two values sec, nsec
-- @release Released under DualBSD/LGPG
-- @copyright Markus Klotzbuecher, Katholieke Universiteit Leuven, Belgium.
local math = math
module("time")
-- constants
local ns_per_s = 1000000000
local us_per_s = 1000000
--- Normalize time.
-- @param sec seconds
-- @param nsec nanoseconds
function normalize(sec, nsec)
-- normalize too big ns
while(nsec>ns_per_s) do
sec = sec + 1
nsec = nsec - ns_per_s
end
-- normalize to small ns
while( nsec <= -ns_per_s) do
sec = sec - 1
nsec = nsec + ns_per_s
end
-- fix special negative cases
--
-- perferred: either sec and ns less than zero or sec=0 and ns less
-- than zero.
if (sec>0 and nsec<0) then
sec = sec - 1
nsec = nsec + ns_per_s
end
-- prefer negative sign on nsec
if(sec<0 and nsec>0) then
sec=sec + 1
nsec=nsec-ns_per_s
end
return sec, nsec
end
--- Subtract a timespec from another and normalize
-- @param a timespec to subtract from
-- @param b timespec to subtract
function sub(a, b)
local sec = a.sec - b.sec
local nsec = a.nsec - b.nsec
return normalize(sec, nsec)
end
--- Add a timespec from another and normalize
-- @param a timespec a
-- @param b timespec b
function add(a, b)
local sec = a.sec + b.sec
local nsec = a.nsec + b.nsec
return normalize(sec, nsec)
end
--- Divide a timespec inplace
-- @param t timespec to divide
-- @param d divisor
function div(t, d)
return normalize(t.sec / d, t.nsec / d)
end
--- Compare to timespecs
-- @result return 1 if t1 is greater than t2, -1 if t1 is less than t2 and 0 if t1 and t2 are equal
function cmp(t1, t2)
if(t1.sec > t2.sec) then return 1
elseif (t1.sec < t2.sec) then return -1
elseif (t1.nsec > t2.nsec) then return 1
elseif (t1.nsec < t2.nsec) then return -1
else return 0 end
end
-- Return absolute timespec.
-- @param ts timespec
-- @return absolute sec
-- @return absolute nsec
function abs(ts)
return math.abs(ts.sec), math.abs(ts.nsec)
end
--- Convert timespec to microseconds
-- @param ts timespec
-- @result number of microseconds
function ts2us(ts)
return ts.sec * us_per_s + ts.nsec / 1000
end
--- Convert a timespec to a string (in micro-seconds)
--- for pretty printing purposes
function ts2str(ts)
return ts2us(ts) .. "us"
end
--- Convert timespec to us
-- @param sec
-- @param nsec
-- @return time is us
function tous(sec, nsec)
return sec * us_per_s + nsec / 1000
end
--- Convert timespec to us string
-- @param sec
-- @param nsec
-- @return time string
function tostr_us(sec, nsec)
return tous(sec, nsec) .. "us"
end