1
2
3
4 import errno
5 import stat
6
7 import portage
8 from portage import os
9 from portage.util import writemsg
10
11 import sys
12 if sys.hexversion >= 0x3000000:
13 long = int
14
16
17 short_desc = "Generate a metadata index for binary packages"
18
21 name = staticmethod(name)
22
29
31
32 if "MD5" not in data:
33 return True
34
35 size = data.get("SIZE")
36 if size is None:
37 return True
38
39 mtime = data.get("MTIME")
40 if mtime is None:
41 return True
42
43 pkg_path = self._bintree.getname(cpv)
44 try:
45 s = os.lstat(pkg_path)
46 except OSError as e:
47 if e.errno not in (errno.ENOENT, errno.ESTALE):
48 raise
49
50
51 return False
52
53 try:
54 if long(mtime) != s[stat.ST_MTIME]:
55 return True
56 if long(size) != long(s.st_size):
57 return True
58 except ValueError:
59 return True
60
61 return False
62
63 - def check(self, **kwargs):
87
88 - def fix(self, **kwargs):
89 onProgress = kwargs.get('onProgress', None)
90 bintree = self._bintree
91 cpv_all = self._bintree.dbapi.cpv_all()
92 cpv_all.sort()
93 missing = []
94 maxval = 0
95 if onProgress:
96 onProgress(maxval, 0)
97 pkgindex = self._pkgindex
98 missing = []
99 metadata = {}
100 for d in pkgindex.packages:
101 metadata[d["CPV"]] = d
102
103 for i, cpv in enumerate(cpv_all):
104 d = metadata.get(cpv)
105 if not d or self._need_update(cpv, d):
106 missing.append(cpv)
107
108 stale = set(metadata).difference(cpv_all)
109 if missing or stale:
110 from portage import locks
111 pkgindex_lock = locks.lockfile(
112 self._pkgindex_file, wantnewlockfile=1)
113 try:
114
115 bintree._populate()
116 cpv_all = self._bintree.dbapi.cpv_all()
117 cpv_all.sort()
118
119 pkgindex = bintree._load_pkgindex()
120 self._pkgindex = pkgindex
121
122 metadata = {}
123 for d in pkgindex.packages:
124 metadata[d["CPV"]] = d
125
126
127 del missing[:]
128 for i, cpv in enumerate(cpv_all):
129 d = metadata.get(cpv)
130 if not d or self._need_update(cpv, d):
131 missing.append(cpv)
132
133 maxval = len(missing)
134 for i, cpv in enumerate(missing):
135 try:
136 metadata[cpv] = bintree._pkgindex_entry(cpv)
137 except portage.exception.InvalidDependString:
138 writemsg("!!! Invalid binary package: '%s'\n" % \
139 bintree.getname(cpv), noiselevel=-1)
140
141 if onProgress:
142 onProgress(maxval, i+1)
143
144 for cpv in set(metadata).difference(
145 self._bintree.dbapi.cpv_all()):
146 del metadata[cpv]
147
148
149
150 bintree.populated = False
151
152 del pkgindex.packages[:]
153 pkgindex.packages.extend(metadata.values())
154 bintree._pkgindex_write(self._pkgindex)
155
156 finally:
157 locks.unlockfile(pkgindex_lock)
158
159 if onProgress:
160 if maxval == 0:
161 maxval = 1
162 onProgress(maxval, maxval)
163 return None
164