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
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
|
import commands as cmd
import subprocess as sp
import os, portage, shlex
from os.path import join as pjoin
import benchutils
class InstallException(Exception):
def __init__(self, command, logfile):
self.command = command
self.logfile = logfile
def _getEnv(root='/', envAdds={}):
denv = os.environ.copy()
#PATH
denv['PATH'] = ':'.join([pjoin(root, i) for i in ('bin', 'usr/bin')])
if os.environ.has_key('PATH'):
denv['PATH'] += ':' + os.environ['PATH']
denv['ROOTPATH'] = denv['PATH']
#LIBRARY_PATH
denv['LIBRARY_PATH'] = ':'.join([pjoin(root, i) for i in \
('usr/lib', 'usr/lib64', 'usr/lib32')])
if os.environ.has_key('LIBRARY_PATH'):
denv['LIBRARY_PATH'] += ':' + os.environ['LIBRARY_PATH']
#LD_LIBRARY_PATH
denv['LD_LIBRARY_PATH'] = ':'.join([pjoin(root, i) for i in \
('usr/lib', 'usr/lib64', 'usr/lib32')])
if os.environ.has_key('LD_LIBRARY_PATH'):
denv['LD_LIBRARY_PATH'] += ':' + os.environ['LD_LIBRARY_PATH']
#INCLUDE_PATH
denv['INCLUDE_PATH'] = ':'.join([pjoin(root, i) for i in ('usr/include',)])
if os.environ.has_key('INCLUDE_PATH'):
denv['INCLUDE_PATH'] += ':' + os.environ['INCLUDE_PATH']
# Adds
for k,v in envAdds.items():
denv[k] = v
return denv
def available_packages(pattern):
"""Returns a list of packages matching the given pattern.
The packages are returned as (category, package, version, revision) tuple.
No test for keywords or mask is performed. The function just returns
every matching pattern in the portage tree and installed overlays.
"""
return [portage.catpkgsplit(l) \
for l in cmd.getoutput('equery -q list -po ' + pattern).split()]
def normalize_cpv(cpv):
if type(cpv) == type(''):
try:
cpv_ = portage.catpkgsplit(cpv)
cpv_[-1]
cpv = cpv_
except:
cpv = available_packages(cpv)[-1]
if cpv[-1] != 'r0':
return '%s/%s-%s-%s' % cpv
else:
return '%s/%s-%s' % cpv[:-1]
def get_dependencies(package, env={}, split=False):
pkg = normalize_cpv(package)
cmd = ['emerge', '--ignore-default-opts', '='+pkg, '-poq']
proc = sp.Popen(cmd, stdout=sp.PIPE, stderr=sp.PIPE, env=env)
output = proc.communicate()[0]
if proc.returncode != 0:
return []
lines = output.strip().split('\n')
if not lines[0]:
return []
if split:
return [portage.catpkgsplit(shlex.split(l.strip())[-1]) for l in lines]
else:
return [shlex.split(l.strip())[-1] for l in lines]
def install_dependencies(package, env={}, root='/',
pkgdir='usr/portage/packages', logdir=None):
if logdir is None:
logdir = "/var/log/benchmarks/.unordered"
# Adjust environment
denv = _getEnv(root, dict(PKGDIR=pkgdir))
# Retrieve dependencies
deps = get_dependencies(package, denv, False)
for i,d in enumerate(deps):
logfile = pjoin(logdir, 'emergedep_%i.log' % i)
install_package(d, env, root, pkgdir, logfile)
def install_package(package, env={}, root='/', pkgdir='usr/portage/packages',
logfile=None):
"""Emerge a package in the given root.
package is the package to be emerged. It has to be a tuple
(category, package, version, revision).
env is a dictionary of KEY:VALUE pairs describing the environment changes
the package will be emerged with. It is useful to specifiy the compilers and
compiler flags. It is safe to use ACCEPT_KEYWORDS=* for testing purposes.
root is the directory where the packaged will be emerged. A non-root user
can use this function, provided he has write access to that directory.
pkgdir is the directory where the binary package will be placed. The user
has to be able to write in this directory.
The function has no return value and raises an exception in case of building
or emerging failure. Note: dependencies will NOT be emerged!
"""
envAdds = env.copy()
envAdds['PKGDIR'] = pkgdir
denv = _getEnv(root, envAdds)
del envAdds
# Retrieve package string
pkg = normalize_cpv(package)
# Execute emerge command and log the results
if logfile is not None:
fout = file(logfile, 'w')
fout.flush()
else:
fout = sp.PIPE
cmd = ['emerge', '--ignore-default-opts', '-OB', '=' + pkg]
p = sp.Popen(cmd, env=denv, stdout=fout, stderr=sp.STDOUT)
p.wait()
if p.returncode != 0:
# In case of error, print the whole emerge command
raise InstallException(' '.join(cmd), logfile)
# Unpack package onto root
benchutils.mkdir(pkgdir)
benchutils.mkdir(root)
archive = pjoin(pkgdir, pkg+'.tbz2')
tarcmd = ['tar', 'xjvf', archive, '-C', root]
cl = ' '.join(tarcmd)
if logfile is not None:
fout.write('\n\n' + 80*'#' + '\n\n')
fout.write(cl + '\n' + 80*'-' + '\n')
p = sp.Popen(tarcmd, stdout=fout, stderr=sp.STDOUT)
p.wait()
if p.returncode != 0:
# In case of error, print the whole emerge command
raise InstallException(cl, logfile)
if logfile is not None:
fout.close()
if __name__ == '__main__':
# Just a test
from pprint import pprint
pprint(get_dependencies('sci-libs/blas-reference-3.3.1-r1'))
|