Commit | Line | Data |
---|---|---|
bd3cd7c5 JD |
1 | import math |
2 | import re | |
3 | import time | |
4 | import datetime | |
5 | import socket | |
6 | import struct | |
7 | import sys | |
8 | from linuxautomaton import sv | |
9 | ||
10 | NSEC_PER_SEC = 1000000000 | |
11 | MSEC_PER_NSEC = 1000000 | |
12 | ||
13 | O_CLOEXEC = 0o2000000 | |
14 | ||
15 | ||
16 | # imported from include/linux/kdev_t.h | |
17 | def kdev_major_minor(dev): | |
18 | MINORBITS = 20 | |
19 | MINORMASK = ((1 << MINORBITS) - 1) | |
20 | major = dev >> MINORBITS | |
21 | minor = dev & MINORMASK | |
22 | return "(%d,%d)" % (major, minor) | |
23 | ||
24 | ||
25 | def get_disk(dev, disks): | |
26 | if dev not in disks: | |
27 | d = sv.Disk() | |
28 | d.name = "%d" % dev | |
29 | d.prettyname = kdev_major_minor(dev) | |
30 | disks[dev] = d | |
31 | else: | |
32 | d = disks[dev] | |
33 | return d | |
34 | ||
35 | ||
36 | def convert_size(size, padding_after=False, padding_before=False): | |
37 | if padding_after and size < 1024: | |
38 | space_after = " " | |
39 | else: | |
40 | space_after = "" | |
41 | if padding_before and size < 1024: | |
42 | space_before = " " | |
43 | else: | |
44 | space_before = "" | |
45 | if size <= 0: | |
46 | return "0 " + space_before + "B" + space_after | |
47 | size_name = ("B", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB") | |
48 | i = int(math.floor(math.log(size, 1024))) | |
49 | p = math.pow(1024, i) | |
50 | s = round(size/p, 2) | |
51 | if (s > 0): | |
52 | try: | |
8e05871d JD |
53 | v = "%0.02f" % s |
54 | return '%s %s%s%s' % (v, space_before, size_name[i], space_after) | |
bd3cd7c5 JD |
55 | except: |
56 | print(i, size_name) | |
57 | raise Exception("Too big to be true") | |
58 | else: | |
59 | return '0 B' | |
60 | ||
61 | ||
62 | def is_multi_day_trace_collection(handle): | |
63 | y = m = d = -1 | |
64 | for h in handle.values(): | |
65 | if y == -1: | |
66 | y = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_year | |
67 | m = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_mon | |
68 | d = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_mday | |
69 | _y = time.localtime(h.timestamp_end/NSEC_PER_SEC).tm_year | |
70 | _m = time.localtime(h.timestamp_end/NSEC_PER_SEC).tm_mon | |
71 | _d = time.localtime(h.timestamp_end/NSEC_PER_SEC).tm_mday | |
72 | if y != _y: | |
73 | return True | |
74 | elif m != _m: | |
75 | return True | |
76 | elif d != _d: | |
77 | return True | |
78 | return False | |
79 | ||
80 | ||
81 | def trace_collection_date(handle): | |
82 | if is_multi_day_trace_collection(handle): | |
83 | return None | |
84 | for h in handle.values(): | |
85 | y = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_year | |
86 | m = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_mon | |
87 | d = time.localtime(h.timestamp_begin/NSEC_PER_SEC).tm_mday | |
88 | return (y, m, d) | |
89 | ||
90 | ||
91 | def extract_timerange(handle, timerange, gmt): | |
92 | p = re.compile('^\[(?P<begin>.*),(?P<end>.*)\]$') | |
93 | if not p.match(timerange): | |
94 | return None | |
95 | b = p.search(timerange).group("begin").strip() | |
96 | e = p.search(timerange).group("end").strip() | |
97 | begin = date_to_epoch_nsec(handle, b, gmt) | |
98 | if begin is None: | |
99 | return (None, None) | |
100 | end = date_to_epoch_nsec(handle, e, gmt) | |
101 | if end is None: | |
102 | return (None, None) | |
103 | return (begin, end) | |
104 | ||
105 | ||
106 | def date_to_epoch_nsec(handle, date, gmt): | |
107 | # match 2014-12-12 17:29:43.802588035 or 2014-12-12T17:29:43.802588035 | |
108 | p1 = re.compile('^(?P<year>\d\d\d\d)-(?P<mon>[01]\d)-' | |
109 | '(?P<day>[0123]\d)[\sTt]' | |
110 | '(?P<hour>\d\d):(?P<min>\d\d):(?P<sec>\d\d).' | |
111 | '(?P<nsec>\d\d\d\d\d\d\d\d\d)$') | |
112 | # match 2014-12-12 17:29:43 or 2014-12-12T17:29:43 | |
113 | p2 = re.compile('^(?P<year>\d\d\d\d)-(?P<mon>[01]\d)-' | |
114 | '(?P<day>[0123]\d)[\sTt]' | |
115 | '(?P<hour>\d\d):(?P<min>\d\d):(?P<sec>\d\d)$') | |
116 | # match 17:29:43.802588035 | |
117 | p3 = re.compile('^(?P<hour>\d\d):(?P<min>\d\d):(?P<sec>\d\d).' | |
118 | '(?P<nsec>\d\d\d\d\d\d\d\d\d)$') | |
119 | # match 17:29:43 | |
120 | p4 = re.compile('^(?P<hour>\d\d):(?P<min>\d\d):(?P<sec>\d\d)$') | |
121 | ||
122 | if p1.match(date): | |
123 | year = p1.search(date).group("year") | |
124 | month = p1.search(date).group("mon") | |
125 | day = p1.search(date).group("day") | |
126 | hour = p1.search(date).group("hour") | |
127 | minute = p1.search(date).group("min") | |
128 | sec = p1.search(date).group("sec") | |
129 | nsec = p1.search(date).group("nsec") | |
130 | elif p2.match(date): | |
131 | year = p2.search(date).group("year") | |
132 | month = p2.search(date).group("mon") | |
133 | day = p2.search(date).group("day") | |
134 | hour = p2.search(date).group("hour") | |
135 | minute = p2.search(date).group("min") | |
136 | sec = p2.search(date).group("sec") | |
137 | nsec = 0 | |
138 | elif p3.match(date): | |
139 | d = trace_collection_date(handle) | |
140 | if d is None: | |
141 | print("Use the format 'yyyy-mm-dd hh:mm:ss[.nnnnnnnnn]' " | |
142 | "for multi-day traces") | |
143 | return None | |
144 | year = d[0] | |
145 | month = d[1] | |
146 | day = d[2] | |
147 | hour = p3.search(date).group("hour") | |
148 | minute = p3.search(date).group("min") | |
149 | sec = p3.search(date).group("sec") | |
150 | nsec = p3.search(date).group("nsec") | |
151 | elif p4.match(date): | |
152 | d = trace_collection_date(handle) | |
153 | if d is None: | |
154 | print("Use the format 'yyyy-mm-dd hh:mm:ss[.nnnnnnnnn]' " | |
155 | "for multi-day traces") | |
156 | return None | |
157 | year = d[0] | |
158 | month = d[1] | |
159 | day = d[2] | |
160 | hour = p4.search(date).group("hour") | |
161 | minute = p4.search(date).group("min") | |
162 | sec = p4.search(date).group("sec") | |
163 | nsec = 0 | |
164 | else: | |
165 | return None | |
166 | ||
167 | d = datetime.datetime(int(year), int(month), int(day), int(hour), | |
168 | int(minute), int(sec)) | |
169 | if gmt: | |
170 | d = d + datetime.timedelta(seconds=time.timezone) | |
171 | return int(d.timestamp()) * NSEC_PER_SEC + int(nsec) | |
172 | ||
173 | ||
174 | def process_date_args(command): | |
175 | command._arg_multi_day = is_multi_day_trace_collection(command._handle) | |
176 | if command._arg_timerange: | |
177 | (command._arg_begin, command._arg_end) = \ | |
178 | extract_timerange(command._handle, command._arg_timerange, | |
179 | command._arg_gmt) | |
180 | if command._arg_begin is None or command._arg_end is None: | |
181 | print("Invalid timeformat") | |
182 | sys.exit(1) | |
183 | else: | |
184 | if command._arg_begin: | |
185 | command._arg_begin = date_to_epoch_nsec(command._handle, | |
186 | command._arg_begin, | |
187 | command._arg_gmt) | |
188 | if command._arg_begin is None: | |
189 | print("Invalid timeformat") | |
190 | sys.exit(1) | |
191 | if command._arg_end: | |
192 | command._arg_end = date_to_epoch_nsec(command._handle, | |
193 | command._arg_end, | |
194 | command._arg_gmt) | |
195 | if command._arg_end is None: | |
196 | print("Invalid timeformat") | |
197 | sys.exit(1) | |
198 | ||
199 | ||
200 | def ns_to_asctime(ns): | |
201 | return time.asctime(time.localtime(ns/NSEC_PER_SEC)) | |
202 | ||
203 | ||
204 | def ns_to_hour(ns): | |
205 | d = time.localtime(ns/NSEC_PER_SEC) | |
206 | return "%02d:%02d:%02d" % (d.tm_hour, d.tm_min, d.tm_sec) | |
207 | ||
208 | ||
209 | def ns_to_hour_nsec(ns, multi_day=False, gmt=False): | |
210 | if gmt: | |
211 | d = time.gmtime(ns/NSEC_PER_SEC) | |
212 | else: | |
213 | d = time.localtime(ns/NSEC_PER_SEC) | |
214 | if multi_day: | |
215 | return "%04d-%02d-%02d %02d:%02d:%02d.%09d" % (d.tm_year, d.tm_mon, | |
216 | d.tm_mday, d.tm_hour, | |
217 | d.tm_min, d.tm_sec, | |
218 | ns % NSEC_PER_SEC) | |
219 | else: | |
220 | return "%02d:%02d:%02d.%09d" % (d.tm_hour, d.tm_min, d.tm_sec, | |
221 | ns % NSEC_PER_SEC) | |
222 | ||
223 | ||
224 | def ns_to_sec(ns): | |
225 | return "%lu.%09u" % (ns/NSEC_PER_SEC, ns % NSEC_PER_SEC) | |
226 | ||
227 | ||
228 | def ns_to_day(ns): | |
229 | d = time.localtime(ns/NSEC_PER_SEC) | |
230 | return "%04d-%02d-%02d" % (d.tm_year, d.tm_mon, d.tm_mday) | |
231 | ||
232 | ||
233 | def sec_to_hour(ns): | |
234 | d = time.localtime(ns) | |
235 | return "%02d:%02d:%02d" % (d.tm_hour, d.tm_min, d.tm_sec) | |
236 | ||
237 | ||
238 | def sec_to_nsec(sec): | |
239 | return sec * NSEC_PER_SEC | |
240 | ||
241 | ||
242 | def seq_to_ipv4(ip): | |
243 | return "{}.{}.{}.{}".format(ip[0], ip[1], ip[2], ip[3]) | |
244 | ||
245 | ||
246 | def int_to_ipv4(ip): | |
247 | return socket.inet_ntoa(struct.pack("!I", ip)) | |
248 | ||
249 | ||
250 | def str_to_bytes(value): | |
251 | num = "" | |
252 | unit = "" | |
253 | for i in value: | |
254 | if i.isdigit() or i == ".": | |
255 | num = num + i | |
256 | elif i.isalnum(): | |
257 | unit = unit + i | |
258 | num = float(num) | |
259 | if len(unit) == 0: | |
260 | return int(num) | |
261 | if unit in ["B"]: | |
262 | return int(num) | |
263 | if unit in ["k", "K", "kB", "KB"]: | |
264 | return int(num * 1024) | |
265 | if unit in ["m", "M", "mB", "MB"]: | |
266 | return int(num * 1024 * 1024) | |
267 | if unit in ["g", "G", "gB", "GB"]: | |
268 | return int(num * 1024 * 1024 * 1024) | |
269 | if unit in ["t", "T", "tB", "TB"]: | |
270 | return int(num * 1024 * 1024 * 1024 * 1024) | |
271 | print("Unit", unit, "not understood") | |
272 | return None | |
273 | ||
274 | ||
275 | def get_v4_addr_str(ip): | |
276 | # depending on the version of lttng-modules, the v4addr is a | |
277 | # string (< 2.6) or sequence (>= 2.6) | |
278 | try: | |
279 | return seq_to_ipv4(ip) | |
280 | except TypeError: | |
281 | return int_to_ipv4(ip) |