1 |
Author: zmedico |
2 |
Date: 2008-05-27 04:04:28 +0000 (Tue, 27 May 2008) |
3 |
New Revision: 10440 |
4 |
|
5 |
Modified: |
6 |
main/trunk/pym/_emerge/__init__.py |
7 |
main/trunk/pym/portage/dep.py |
8 |
Log: |
9 |
Fix USE dep matching support in match_from_list() so that it checks |
10 |
to make sure the package supports all specified IUSE. This involves |
11 |
updating all Package, FakeVartree, and BlockerDB constructor |
12 |
arguments to implement a Package.root_config attribute that's used |
13 |
to access implicit IUSE. |
14 |
|
15 |
|
16 |
Modified: main/trunk/pym/_emerge/__init__.py |
17 |
=================================================================== |
18 |
--- main/trunk/pym/_emerge/__init__.py 2008-05-27 00:50:40 UTC (rev 10439) |
19 |
+++ main/trunk/pym/_emerge/__init__.py 2008-05-27 04:04:28 UTC (rev 10440) |
20 |
@@ -399,6 +399,7 @@ |
21 |
self.spinner = spinner |
22 |
self.verbose = verbose |
23 |
self.searchdesc = searchdesc |
24 |
+ self.root_config = root_config |
25 |
self.setconfig = root_config.setconfig |
26 |
|
27 |
def fake_portdb(): |
28 |
@@ -470,7 +471,7 @@ |
29 |
elif built: |
30 |
pkg_type = "binary" |
31 |
return visible(self.settings, |
32 |
- Package(type_name=pkg_type, root=self.settings["ROOT"], |
33 |
+ Package(type_name=pkg_type, root_config=self.root_config, |
34 |
cpv=cpv, built=built, installed=installed, metadata=metadata)) |
35 |
|
36 |
def _xmatch(self, level, atom): |
37 |
@@ -729,6 +730,7 @@ |
38 |
def __init__(self, settings, trees, setconfig): |
39 |
self.trees = trees |
40 |
self.settings = settings |
41 |
+ self.iuse_implicit = tuple(sorted(settings._get_implicit_iuse())) |
42 |
self.root = self.settings["ROOT"] |
43 |
self.setconfig = setconfig |
44 |
self.sets = self.setconfig.getSets() |
45 |
@@ -741,7 +743,7 @@ |
46 |
in world since system atoms can only match one slot while world atoms can |
47 |
be greedy with respect to slots. Unslotted system packages will not be |
48 |
stored in world.""" |
49 |
- pkg = Package(cpv=pkg_key, metadata=metadata) |
50 |
+ pkg = Package(cpv=pkg_key, root_config=root_config, metadata=metadata) |
51 |
arg_atom = args_set.findAtomForPackage(pkg) |
52 |
if not arg_atom: |
53 |
return None |
54 |
@@ -977,11 +979,14 @@ |
55 |
user doesn't necessarily need write access to the vardb in cases where |
56 |
global updates are necessary (updates are performed when necessary if there |
57 |
is not a matching ebuild in the tree).""" |
58 |
- def __init__(self, real_vartree, portdb, |
59 |
- db_keys, pkg_cache, acquire_lock=1): |
60 |
+ def __init__(self, root_config, pkg_cache=None, acquire_lock=1): |
61 |
+ if pkg_cache is None: |
62 |
+ pkg_cache = {} |
63 |
+ real_vartree = root_config.trees["vartree"] |
64 |
+ portdb = root_config.trees["porttree"].dbapi |
65 |
self.root = real_vartree.root |
66 |
self.settings = real_vartree.settings |
67 |
- mykeys = db_keys[:] |
68 |
+ mykeys = list(Package.metadata_keys) |
69 |
for required_key in ("COUNTER", "SLOT"): |
70 |
if required_key not in mykeys: |
71 |
mykeys.append(required_key) |
72 |
@@ -1022,7 +1027,7 @@ |
73 |
if pkg is None: |
74 |
pkg = Package(built=True, cpv=cpv, |
75 |
installed=True, metadata=metadata, |
76 |
- root=self.root, type_name="installed") |
77 |
+ root_config=root_config, type_name="installed") |
78 |
self._pkg_cache[pkg] = pkg |
79 |
self.dbapi.cpv_inject(pkg) |
80 |
real_dbapi.flush_cache() |
81 |
@@ -1159,7 +1164,7 @@ |
82 |
if metadata is None: |
83 |
mreasons = ["corruption"] |
84 |
else: |
85 |
- pkg = Package(type_name=pkg_type, root=root_config.root, |
86 |
+ pkg = Package(type_name=pkg_type, root_config=root_config, |
87 |
cpv=cpv, built=built, installed=installed, metadata=metadata) |
88 |
mreasons = get_masking_status(pkg, pkgsettings, root_config) |
89 |
return metadata, mreasons |
90 |
@@ -1267,9 +1272,9 @@ |
91 |
class Package(Task): |
92 |
__slots__ = ("built", "cpv", "depth", |
93 |
"installed", "metadata", "onlydeps", "operation", |
94 |
- "root", "type_name", |
95 |
- "category", "cp", "cpv_split", |
96 |
- "pf", "pv_split", "slot", "slot_atom", "use") |
97 |
+ "root_config", "type_name", |
98 |
+ "category", "cp", "cpv_split", "iuse", |
99 |
+ "pf", "pv_split", "root", "slot", "slot_atom", "use") |
100 |
|
101 |
metadata_keys = [ |
102 |
"CHOST", "COUNTER", "DEPEND", "EAPI", "IUSE", "KEYWORDS", |
103 |
@@ -1278,6 +1283,7 @@ |
104 |
|
105 |
def __init__(self, **kwargs): |
106 |
Task.__init__(self, **kwargs) |
107 |
+ self.root = self.root_config.root |
108 |
self.metadata = self._metadata_wrapper(self, self.metadata) |
109 |
self.cp = portage.cpv_getkey(self.cpv) |
110 |
self.slot_atom = portage.dep.Atom("%s:%s" % (self.cp, self.slot)) |
111 |
@@ -1286,13 +1292,51 @@ |
112 |
self.pv_split = self.cpv_split[1:] |
113 |
|
114 |
class _use(object): |
115 |
+ |
116 |
+ __slots__ = ("__weakref__", "enabled") |
117 |
+ |
118 |
def __init__(self, use): |
119 |
self.enabled = frozenset(use) |
120 |
|
121 |
+ class _iuse(object): |
122 |
+ |
123 |
+ __slots__ = ("__weakref__", "all", "enabled", "disabled", "iuse_implicit", "regex", "tokens") |
124 |
+ |
125 |
+ def __init__(self, tokens, iuse_implicit): |
126 |
+ self.tokens = tuple(tokens) |
127 |
+ self.iuse_implicit = iuse_implicit |
128 |
+ enabled = [] |
129 |
+ disabled = [] |
130 |
+ other = [] |
131 |
+ for x in tokens: |
132 |
+ prefix = x[:1] |
133 |
+ if prefix == "+": |
134 |
+ enabled.append(x[1:]) |
135 |
+ elif prefix == "-": |
136 |
+ disabled.append(x[1:]) |
137 |
+ else: |
138 |
+ other.append(x) |
139 |
+ self.enabled = frozenset(enabled) |
140 |
+ self.disabled = frozenset(disabled) |
141 |
+ self.all = frozenset(chain(enabled, disabled, other)) |
142 |
+ |
143 |
+ def __getattribute__(self, name): |
144 |
+ if name == "regex": |
145 |
+ try: |
146 |
+ return object.__getattribute__(self, "regex") |
147 |
+ except AttributeError: |
148 |
+ all = object.__getattribute__(self, "all") |
149 |
+ iuse_implicit = object.__getattribute__(self, "iuse_implicit") |
150 |
+ self.regex = re.compile("^(%s)$" % "|".join( |
151 |
+ chain((re.escape(x) for x in all), iuse_implicit))) |
152 |
+ return object.__getattribute__(self, name) |
153 |
+ |
154 |
class _metadata_wrapper(dict): |
155 |
""" |
156 |
Detect metadata updates and synchronize Package attributes. |
157 |
""" |
158 |
+ _wrapped_keys = frozenset(["IUSE", "SLOT", "USE"]) |
159 |
+ |
160 |
def __init__(self, pkg, metadata): |
161 |
dict.__init__(self) |
162 |
self._pkg = pkg |
163 |
@@ -1306,11 +1350,19 @@ |
164 |
|
165 |
def __setitem__(self, k, v): |
166 |
dict.__setitem__(self, k, v) |
167 |
- if k == "USE": |
168 |
- self._pkg.use = self._pkg._use(v.split()) |
169 |
- elif k == "SLOT": |
170 |
- self._pkg.slot = v |
171 |
+ if k in self._wrapped_keys: |
172 |
+ getattr(self, "_set_" + k.lower())(k, v) |
173 |
|
174 |
+ def _set_iuse(self, k, v): |
175 |
+ self._pkg.iuse = self._pkg._iuse( |
176 |
+ v.split(), self._pkg.root_config.iuse_implicit) |
177 |
+ |
178 |
+ def _set_slot(self, k, v): |
179 |
+ self._pkg.slot = v |
180 |
+ |
181 |
+ def _set_use(self, k, v): |
182 |
+ self._pkg.use = self._pkg._use(v.split()) |
183 |
+ |
184 |
def _get_hash_key(self): |
185 |
hash_key = getattr(self, "_hash_key", None) |
186 |
if hash_key is None: |
187 |
@@ -1547,9 +1599,10 @@ |
188 |
|
189 |
class BlockerDB(object): |
190 |
|
191 |
- def __init__(self, vartree, portdb): |
192 |
- self._vartree = vartree |
193 |
- self._portdb = portdb |
194 |
+ def __init__(self, root_config): |
195 |
+ self._root_config = root_config |
196 |
+ self._vartree = root_config.trees["vartree"] |
197 |
+ self._portdb = root_config.trees["porttree"].dbapi |
198 |
self._blocker_cache = \ |
199 |
BlockerCache(self._vartree.root, vartree.dbapi) |
200 |
self._dep_check_trees = { self._vartree.root : { |
201 |
@@ -1564,9 +1617,7 @@ |
202 |
settings = self._vartree.settings |
203 |
stale_cache = set(blocker_cache) |
204 |
fake_vartree = \ |
205 |
- FakeVartree(self._vartree, |
206 |
- self._portdb, Package.metadata_keys, {}, |
207 |
- acquire_lock=acquire_lock) |
208 |
+ FakeVartree(self._root_config, acquire_lock=acquire_lock) |
209 |
vardb = fake_vartree.dbapi |
210 |
installed_pkgs = list(vardb) |
211 |
|
212 |
@@ -1842,9 +1893,8 @@ |
213 |
for tree in ("porttree", "bintree"): |
214 |
self.trees[myroot][tree] = trees[myroot][tree] |
215 |
self.trees[myroot]["vartree"] = \ |
216 |
- FakeVartree(trees[myroot]["vartree"], |
217 |
- trees[myroot]["porttree"].dbapi, |
218 |
- self._mydbapi_keys, self._pkg_cache) |
219 |
+ FakeVartree(trees[myroot]["root_config"], |
220 |
+ pkg_cache=self._pkg_cache) |
221 |
self.pkgsettings[myroot] = portage.config( |
222 |
clone=self.trees[myroot]["vartree"].settings) |
223 |
self._slot_pkg_map[myroot] = {} |
224 |
@@ -1855,14 +1905,10 @@ |
225 |
# have after new packages have been installed. |
226 |
fakedb = PackageVirtualDbapi(vardb.settings) |
227 |
if preload_installed_pkgs: |
228 |
- for cpv in vardb.cpv_all(): |
229 |
+ for pkg in vardb: |
230 |
self.spinner.update() |
231 |
- metadata = dict(izip(self._mydbapi_keys, |
232 |
- vardb.aux_get(cpv, self._mydbapi_keys))) |
233 |
- pkg = Package(built=True, cpv=cpv, |
234 |
- installed=True, metadata=metadata, |
235 |
- root=myroot, type_name="installed") |
236 |
- self._pkg_cache[pkg] = pkg |
237 |
+ # This triggers metadata updates via FakeVartree. |
238 |
+ vardb.aux_get(pkg.cpv, []) |
239 |
fakedb.cpv_inject(pkg) |
240 |
self.mydbapi[myroot] = fakedb |
241 |
def graph_tree(): |
242 |
@@ -2506,7 +2552,7 @@ |
243 |
return 0, myfavorites |
244 |
metadata = dict(izip(self._mydbapi_keys, |
245 |
bindb.aux_get(mykey, self._mydbapi_keys))) |
246 |
- pkg = Package(type_name="binary", root=myroot, |
247 |
+ pkg = Package(type_name="binary", root_config=root_config, |
248 |
cpv=mykey, built=True, metadata=metadata, |
249 |
onlydeps=onlydeps) |
250 |
self._pkg_cache[pkg] = pkg |
251 |
@@ -2546,7 +2592,7 @@ |
252 |
portdb.aux_get(mykey, self._mydbapi_keys))) |
253 |
pkgsettings.setcpv(mykey, mydb=metadata) |
254 |
metadata["USE"] = pkgsettings["PORTAGE_USE"] |
255 |
- pkg = Package(type_name="ebuild", root=myroot, |
256 |
+ pkg = Package(type_name="ebuild", root_config=root_config, |
257 |
cpv=mykey, metadata=metadata, onlydeps=onlydeps) |
258 |
self._pkg_cache[pkg] = pkg |
259 |
args.append(PackageArg(arg=x, package=pkg, |
260 |
@@ -2895,7 +2941,8 @@ |
261 |
pkgsettings, db, pkg_type, built, installed, db_keys) |
262 |
if atom.use and not mreasons: |
263 |
missing_use.append(Package(built=built, cpv=cpv, |
264 |
- installed=installed, metadata=metadata, root=root)) |
265 |
+ installed=installed, metadata=metadata, |
266 |
+ root_config=root_config)) |
267 |
else: |
268 |
masked_packages.append( |
269 |
(root_config, pkgsettings, cpv, metadata, mreasons)) |
270 |
@@ -2978,6 +3025,7 @@ |
271 |
return ret |
272 |
|
273 |
def _select_pkg_highest_available_imp(self, root, atom, onlydeps=False): |
274 |
+ root_config = self.roots[root] |
275 |
pkgsettings = self.pkgsettings[root] |
276 |
dbs = self._filtered_trees[root]["dbs"] |
277 |
vardb = self.roots[root].trees["vartree"].dbapi |
278 |
@@ -3063,7 +3111,8 @@ |
279 |
continue |
280 |
pkg = Package(built=built, cpv=cpv, |
281 |
installed=installed, metadata=metadata, |
282 |
- onlydeps=onlydeps, root=root, type_name=pkg_type) |
283 |
+ onlydeps=onlydeps, root_config=root_config, |
284 |
+ type_name=pkg_type) |
285 |
metadata = pkg.metadata |
286 |
if not built and ("?" in metadata["LICENSE"] or \ |
287 |
"?" in metadata["PROVIDE"]): |
288 |
@@ -3595,7 +3644,8 @@ |
289 |
uninst_task = Package(built=inst_pkg.built, |
290 |
cpv=inst_pkg.cpv, installed=inst_pkg.installed, |
291 |
metadata=inst_pkg.metadata, |
292 |
- operation="uninstall", root=inst_pkg.root, |
293 |
+ operation="uninstall", |
294 |
+ root_config=inst_pkg.root_config, |
295 |
type_name=inst_pkg.type_name) |
296 |
self._pkg_cache[uninst_task] = uninst_task |
297 |
# Enforce correct merge order with a hard dep. |
298 |
@@ -5207,9 +5257,10 @@ |
299 |
raise portage.exception.PackageNotFound(pkg_key) |
300 |
installed = action == "uninstall" |
301 |
built = pkg_type != "ebuild" |
302 |
+ root_config = self.roots[myroot] |
303 |
pkg = Package(built=built, cpv=pkg_key, |
304 |
installed=installed, metadata=metadata, |
305 |
- operation=action, root=myroot, |
306 |
+ operation=action, root_config=root_config, |
307 |
type_name=pkg_type) |
308 |
if pkg_type == "ebuild": |
309 |
pkgsettings = self.pkgsettings[myroot] |
310 |
@@ -5650,9 +5701,7 @@ |
311 |
for root in trees: |
312 |
self.pkgsettings[root] = portage.config( |
313 |
clone=trees[root]["vartree"].settings) |
314 |
- self._blocker_db[root] = BlockerDB( |
315 |
- trees[root]["vartree"], |
316 |
- trees[root]["porttree"].dbapi) |
317 |
+ self._blocker_db[root] = BlockerDB(trees[root]["root_config"]) |
318 |
self.curval = 0 |
319 |
self._spawned_pids = [] |
320 |
|
321 |
@@ -7788,9 +7837,7 @@ |
322 |
dep_check_trees = {} |
323 |
dep_check_trees[myroot] = {} |
324 |
dep_check_trees[myroot]["vartree"] = \ |
325 |
- FakeVartree(trees[myroot]["vartree"], |
326 |
- trees[myroot]["porttree"].dbapi, |
327 |
- depgraph._mydbapi_keys, pkg_cache) |
328 |
+ FakeVartree(trees[myroot]["root_config"], pkg_cache=pkg_cache) |
329 |
vardb = dep_check_trees[myroot]["vartree"].dbapi |
330 |
# Constrain dependency selection to the installed packages. |
331 |
dep_check_trees[myroot]["porttree"] = dep_check_trees[myroot]["vartree"] |
332 |
|
333 |
Modified: main/trunk/pym/portage/dep.py |
334 |
=================================================================== |
335 |
--- main/trunk/pym/portage/dep.py 2008-05-27 00:50:40 UTC (rev 10439) |
336 |
+++ main/trunk/pym/portage/dep.py 2008-05-27 04:04:28 UTC (rev 10440) |
337 |
@@ -890,11 +890,16 @@ |
338 |
candidate_list = mylist |
339 |
mylist = [] |
340 |
for x in candidate_list: |
341 |
- # Note: IUSE intersection is neglected here since there |
342 |
- # is currently no way to access implicit IUSE. However, IUSE |
343 |
- # filtering can be added elsewhere in the chain. |
344 |
use = getattr(x, "use", None) |
345 |
if use is not None: |
346 |
+ regex = x.iuse.regex |
347 |
+ missing_iuse = False |
348 |
+ for y in mydep.use.required: |
349 |
+ if regex.match(y) is None: |
350 |
+ missing_iuse = True |
351 |
+ break |
352 |
+ if missing_iuse: |
353 |
+ continue |
354 |
if mydep.use.enabled.difference(use.enabled): |
355 |
continue |
356 |
if mydep.use.disabled.intersection(use.enabled): |
357 |
|
358 |
-- |
359 |
gentoo-commits@l.g.o mailing list |