blob: 5a9f188f9d40fb44512a7031f555d9eb33226c0e [file] [log] [blame]
koder aka kdanilov652cd802015-04-13 12:21:07 +03001import re
koder aka kdanilove21d7472015-02-14 19:02:04 -08002import logging
koder aka kdanilov7acd6bd2015-02-12 14:28:30 -08003import threading
4import contextlib
koder aka kdanilov652cd802015-04-13 12:21:07 +03005import subprocess
koder aka kdanilov4643fd62015-02-10 16:20:13 -08006
koder aka kdanilove21d7472015-02-14 19:02:04 -08007
8logger = logging.getLogger("io-perf-tool")
koder aka kdanilov7acd6bd2015-02-12 14:28:30 -08009
10
koder aka kdanilove06762a2015-03-22 23:32:09 +020011def parse_creds(creds):
12 # parse user:passwd@host
13 user, passwd_host = creds.split(":", 1)
14
15 if '@' not in passwd_host:
16 passwd, host = passwd_host, None
17 else:
18 passwd, host = passwd_host.rsplit('@', 1)
19
20 return user, passwd, host
21
22
koder aka kdanilov2c473092015-03-29 17:12:13 +030023class TaksFinished(Exception):
24 pass
koder aka kdanilov4643fd62015-02-10 16:20:13 -080025
koder aka kdanilov2c473092015-03-29 17:12:13 +030026
27class Barrier(object):
28 def __init__(self, count):
29 self.count = count
30 self.curr_count = 0
31 self.cond = threading.Condition()
32 self.exited = False
33
34 def wait(self, timeout=None):
35 with self.cond:
36 if self.exited:
37 raise TaksFinished()
38
39 self.curr_count += 1
40 if self.curr_count == self.count:
41 self.curr_count = 0
42 self.cond.notify_all()
koder aka kdanilov652cd802015-04-13 12:21:07 +030043 return True
koder aka kdanilov4643fd62015-02-10 16:20:13 -080044 else:
koder aka kdanilov2c473092015-03-29 17:12:13 +030045 self.cond.wait(timeout=timeout)
koder aka kdanilov652cd802015-04-13 12:21:07 +030046 return False
koder aka kdanilov4643fd62015-02-10 16:20:13 -080047
koder aka kdanilov2c473092015-03-29 17:12:13 +030048 def exit(self):
49 with self.cond:
50 self.exited = True
koder aka kdanilov7acd6bd2015-02-12 14:28:30 -080051
52
53@contextlib.contextmanager
54def log_error(action, types=(Exception,)):
55 if not action.startswith("!"):
koder aka kdanilove21d7472015-02-14 19:02:04 -080056 logger.debug("Starts : " + action)
koder aka kdanilov7acd6bd2015-02-12 14:28:30 -080057 else:
58 action = action[1:]
59
60 try:
61 yield
62 except Exception as exc:
63 if isinstance(exc, types) and not isinstance(exc, StopIteration):
64 templ = "Error during {0} stage: {1}"
koder aka kdanilove21d7472015-02-14 19:02:04 -080065 logger.debug(templ.format(action, exc.message))
koder aka kdanilov7acd6bd2015-02-12 14:28:30 -080066 raise
67
68
koder aka kdanilov2c473092015-03-29 17:12:13 +030069SMAP = dict(k=1024, m=1024 ** 2, g=1024 ** 3, t=1024 ** 4)
koder aka kdanilov8ad6e812015-03-22 14:42:18 +020070
71
72def ssize_to_b(ssize):
73 try:
koder aka kdanilov2c473092015-03-29 17:12:13 +030074 ssize = ssize.lower()
koder aka kdanilov8ad6e812015-03-22 14:42:18 +020075
koder aka kdanilov2c473092015-03-29 17:12:13 +030076 if ssize.endswith("b"):
77 ssize = ssize[:-1]
78 if ssize[-1] in SMAP:
79 return int(ssize[:-1]) * SMAP[ssize[-1]]
koder aka kdanilov8ad6e812015-03-22 14:42:18 +020080 return int(ssize)
81 except (ValueError, TypeError, AttributeError):
koder aka kdanilov2e928022015-04-08 13:47:15 +030082 raise ValueError("Unknow size format {0!r}".format(ssize))
koder aka kdanilov652cd802015-04-13 12:21:07 +030083
84
85def get_ip_for_target(target_ip):
86 cmd = 'ip route get to'.split(" ") + [target_ip]
87 data = subprocess.Popen(cmd, stdout=subprocess.PIPE).stdout.read()
88
89 rr = r'{0} via [.0-9]+ dev (?P<dev>.*?) src (?P<ip>[.0-9]+)$'
90 rr = rr.replace(" ", r'\s+')
91 rr = rr.format(target_ip.replace('.', r'\.'))
92
93 data_line = data.split("\n")[0].strip()
94 res = re.match(rr, data_line)
95
96 if res is None:
97 raise OSError("Can't define interface for {0}".format(target_ip))
98
99 return res.group('ip')