-
Notifications
You must be signed in to change notification settings - Fork 636
/
zmqversion.py
129 lines (107 loc) · 3.94 KB
/
zmqversion.py
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
119
120
121
122
123
124
125
126
127
128
129
"""A simply script to scrape zmq.h for the zeromq version.
This is similar to the version.sh script in a zeromq source dir, but
it searches for an installed header, rather than in the current dir.
"""
# Copyright (c) PyZMQ Developers
# Distributed under the terms of the Modified BSD License.
import os
import re
import sys
import traceback
from configparser import ConfigParser
from warnings import warn
pjoin = os.path.join
MAJOR_PAT = '^#define +ZMQ_VERSION_MAJOR +[0-9]+$'
MINOR_PAT = '^#define +ZMQ_VERSION_MINOR +[0-9]+$'
PATCH_PAT = '^#define +ZMQ_VERSION_PATCH +[0-9]+$'
def include_dirs_from_path():
"""Check the exec path for include dirs."""
include_dirs = []
for p in os.environ['PATH'].split(os.path.pathsep):
if p.endswith('/'):
p = p[:-1]
if p.endswith('bin'):
include_dirs.append(p[:-3] + 'include')
return include_dirs
def default_include_dirs():
"""Default to just /usr/local/include:/usr/include"""
return ['/usr/local/include', '/usr/include']
def find_zmq_version():
"""check setup.cfg, then /usr/local/include, then /usr/include for zmq.h.
Then scrape zmq.h for the version tuple.
Returns
-------
((major,minor,patch), "/path/to/zmq.h")"""
include_dirs = []
if os.path.exists('setup.cfg'):
cfg = ConfigParser()
cfg.read('setup.cfg')
if 'build_ext' in cfg.sections():
items = cfg.items('build_ext')
for name, val in items:
if name == 'include_dirs':
include_dirs = val.split(os.path.pathsep)
if not include_dirs:
include_dirs = default_include_dirs()
for include in include_dirs:
zmq_h = pjoin(include, 'zmq.h')
if os.path.isfile(zmq_h):
with open(zmq_h) as f:
contents = f.read()
else:
continue
line = re.findall(MAJOR_PAT, contents, re.MULTILINE)[0]
major = int(re.findall('[0-9]+', line)[0])
line = re.findall(MINOR_PAT, contents, re.MULTILINE)[0]
minor = int(re.findall('[0-9]+', line)[0])
line = re.findall(PATCH_PAT, contents, re.MULTILINE)[0]
patch = int(re.findall('[0-9]+', line)[0])
return ((major, minor, patch), zmq_h)
raise OSError("Couldn't find zmq.h")
def ver_str(version):
"""version tuple as string"""
return '.'.join(map(str, version))
def check_zmq_version(min_version):
"""Check that zmq.h has an appropriate version."""
sv = ver_str(min_version)
try:
found, zmq_h = find_zmq_version()
sf = ver_str(found)
if found < min_version:
print(f"This pyzmq requires zeromq >= {sv}")
print(f"but it appears you are building against {zmq_h}")
print(f"which has zeromq {sf}")
sys.exit(1)
except OSError:
msg = '\n'.join(
[
"Couldn't find zmq.h to check for version compatibility.",
"If you see 'undeclared identifier' errors, your ZeroMQ is likely too old.",
f"This pyzmq requires zeromq >= {sv}",
]
)
warn(msg)
except IndexError:
msg = '\n'.join(
[
"Couldn't find ZMQ_VERSION macros in zmq.h to check for version compatibility.",
"This probably means that you have ZeroMQ <= 2.0.9",
"If you see 'undeclared identifier' errors, your ZeroMQ is likely too old.",
f"This pyzmq requires zeromq >= {sv}",
]
)
warn(msg)
except Exception:
traceback.print_exc()
msg = '\n'.join(
[
"Unexpected Error checking for zmq version.",
"If you see 'undeclared identifier' errors, your ZeroMQ is likely too old.",
f"This pyzmq requires zeromq >= {sv}",
]
)
warn(msg)
if __name__ == '__main__':
v, h = find_zmq_version()
print(h)
print(ver_str(v))