Gentoo Archives: gentoo-commits

From: Zac Medico <zmedico@g.o>
To: gentoo-commits@l.g.o
Subject: [gentoo-commits] proj/portage:master commit in: pym/_emerge/
Date: Sun, 13 May 2012 07:32:44
Message-Id: 1336894324.0903cf2a1544d970b286a3e7e1f3276daa4eab9c.zmedico@gentoo
1 commit: 0903cf2a1544d970b286a3e7e1f3276daa4eab9c
2 Author: Zac Medico <zmedico <AT> gentoo <DOT> org>
3 AuthorDate: Sun May 13 07:32:04 2012 +0000
4 Commit: Zac Medico <zmedico <AT> gentoo <DOT> org>
5 CommitDate: Sun May 13 07:32:04 2012 +0000
6 URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=0903cf2a
7
8 depgraph: minimize match_from_list operations
9
10 In _iter_match_pkgs, call match_from_list on one cpv at a time, in
11 order to avoid unnecessary match_from_list comparisons on versions that
12 are never yielded from this method.
13
14 ---
15 pym/_emerge/depgraph.py | 122 ++++++++++++++++++++++++----------------------
16 1 files changed, 64 insertions(+), 58 deletions(-)
17
18 diff --git a/pym/_emerge/depgraph.py b/pym/_emerge/depgraph.py
19 index 4d3b04c..5152d5c 100644
20 --- a/pym/_emerge/depgraph.py
21 +++ b/pym/_emerge/depgraph.py
22 @@ -18,8 +18,10 @@ from portage import os, OrderedDict
23 from portage import _unicode_decode, _unicode_encode, _encodings
24 from portage.const import PORTAGE_PACKAGE_ATOM, USER_CONFIG_PATH
25 from portage.dbapi import dbapi
26 +from portage.dbapi.dep_expand import dep_expand
27 from portage.dep import Atom, best_match_to_list, extract_affecting_use, \
28 - check_required_use, human_readable_required_use, _repo_separator
29 + check_required_use, human_readable_required_use, match_from_list, \
30 + _repo_separator
31 from portage.eapi import eapi_has_strong_blocks, eapi_has_required_use
32 from portage.exception import InvalidAtom, InvalidDependString, PortageException
33 from portage.output import colorize, create_color_func, \
34 @@ -3382,60 +3384,12 @@ class depgraph(object):
35 """
36
37 db = root_config.trees[self.pkg_tree_map[pkg_type]].dbapi
38 -
39 - if hasattr(db, "xmatch"):
40 - # For portdbapi we match only against the cpv, in order
41 - # to bypass unnecessary cache access for things like IUSE
42 - # and SLOT. Later, we cache the metadata in a Package
43 - # instance, and use that for further matching. This
44 - # optimization is especially relevant since
45 - # pordbapi.aux_get() does not cache calls that have
46 - # myrepo or mytree arguments.
47 - cpv_list = db.xmatch("match-all-cpv-only", atom)
48 - else:
49 - cpv_list = db.match(atom)
50 -
51 - # USE=multislot can make an installed package appear as if
52 - # it doesn't satisfy a slot dependency. Rebuilding the ebuild
53 - # won't do any good as long as USE=multislot is enabled since
54 - # the newly built package still won't have the expected slot.
55 - # Therefore, assume that such SLOT dependencies are already
56 - # satisfied rather than forcing a rebuild.
57 + atom_exp = dep_expand(atom, mydb=db, settings=root_config.settings)
58 + cp_list = db.cp_list(atom_exp.cp)
59 + matched_something = False
60 installed = pkg_type == 'installed'
61 - if installed and not cpv_list and atom.slot:
62
63 - if "remove" in self._dynamic_config.myparams:
64 - # We need to search the portdbapi, which is not in our
65 - # normal dbs list, in order to find the real SLOT.
66 - portdb = self._frozen_config.trees[root_config.root]["porttree"].dbapi
67 - db_keys = list(portdb._aux_cache_keys)
68 - dbs = [(portdb, "ebuild", False, False, db_keys)]
69 - else:
70 - dbs = self._dynamic_config._filtered_trees[root_config.root]["dbs"]
71 -
72 - for cpv in db.match(atom.cp):
73 - slot_available = False
74 - for other_db, other_type, other_built, \
75 - other_installed, other_keys in dbs:
76 - try:
77 - if atom.slot == \
78 - other_db.aux_get(cpv, ["SLOT"])[0]:
79 - slot_available = True
80 - break
81 - except KeyError:
82 - pass
83 - if not slot_available:
84 - continue
85 - inst_pkg = self._pkg(cpv, "installed",
86 - root_config, installed=installed, myrepo = atom.repo)
87 - # Remove the slot from the atom and verify that
88 - # the package matches the resulting atom.
89 - if portage.match_from_list(
90 - atom.without_slot, [inst_pkg]):
91 - yield inst_pkg
92 - return
93 -
94 - if cpv_list:
95 + if cp_list:
96 atom_set = InternalPackageSet(initial_atoms=(atom,),
97 allow_repo=True)
98 if atom.repo is None and hasattr(db, "getRepositories"):
99 @@ -3444,8 +3398,13 @@ class depgraph(object):
100 repo_list = [atom.repo]
101
102 # descending order
103 - cpv_list.reverse()
104 - for cpv in cpv_list:
105 + cp_list.reverse()
106 + for cpv in cp_list:
107 + # Call match_from_list on one cpv at a time, in order
108 + # to avoid unnecessary match_from_list comparisons on
109 + # versions that are never yielded from this method.
110 + if not match_from_list(atom_exp, [cpv]):
111 + continue
112 for repo in repo_list:
113
114 try:
115 @@ -3462,14 +3421,61 @@ class depgraph(object):
116 # Make sure that cpv from the current repo satisfies the atom.
117 # This might not be the case if there are several repos with
118 # the same cpv, but different metadata keys, like SLOT.
119 - # Also, for portdbapi, parts of the match that require
120 - # metadata access are deferred until we have cached the
121 - # metadata in a Package instance.
122 + # Also, parts of the match that require metadata access
123 + # are deferred until we have cached the metadata in a
124 + # Package instance.
125 if not atom_set.findAtomForPackage(pkg,
126 modified_use=self._pkg_use_enabled(pkg)):
127 continue
128 + matched_something = True
129 yield pkg
130
131 + # USE=multislot can make an installed package appear as if
132 + # it doesn't satisfy a slot dependency. Rebuilding the ebuild
133 + # won't do any good as long as USE=multislot is enabled since
134 + # the newly built package still won't have the expected slot.
135 + # Therefore, assume that such SLOT dependencies are already
136 + # satisfied rather than forcing a rebuild.
137 + if not matched_something and installed and atom.slot is not None:
138 +
139 + if "remove" in self._dynamic_config.myparams:
140 + # We need to search the portdbapi, which is not in our
141 + # normal dbs list, in order to find the real SLOT.
142 + portdb = self._frozen_config.trees[root_config.root]["porttree"].dbapi
143 + db_keys = list(portdb._aux_cache_keys)
144 + dbs = [(portdb, "ebuild", False, False, db_keys)]
145 + else:
146 + dbs = self._dynamic_config._filtered_trees[root_config.root]["dbs"]
147 +
148 + cp_list = db.cp_list(atom_exp.cp)
149 + if cp_list:
150 + atom_set = InternalPackageSet(
151 + initial_atoms=(atom.without_slot,), allow_repo=True)
152 + atom_exp_without_slot = atom_exp.without_slot
153 + cp_list.reverse()
154 + for cpv in cp_list:
155 + if not match_from_list(atom_exp_without_slot, [cpv]):
156 + continue
157 + slot_available = False
158 + for other_db, other_type, other_built, \
159 + other_installed, other_keys in dbs:
160 + try:
161 + if atom.slot == \
162 + other_db.aux_get(cpv, ["SLOT"])[0]:
163 + slot_available = True
164 + break
165 + except KeyError:
166 + pass
167 + if not slot_available:
168 + continue
169 + inst_pkg = self._pkg(cpv, "installed",
170 + root_config, installed=installed, myrepo=atom.repo)
171 + # Remove the slot from the atom and verify that
172 + # the package matches the resulting atom.
173 + if atom_set.findAtomForPackage(inst_pkg):
174 + yield inst_pkg
175 + return
176 +
177 def _select_pkg_highest_available(self, root, atom, onlydeps=False):
178 cache_key = (root, atom, atom.unevaluated_atom, onlydeps)
179 ret = self._dynamic_config._highest_pkg_cache.get(cache_key)