qahelp={
"CVS/Entries.IO_error":"Attempting to commit, and an IO error was encountered access the Entries file",
"desktop.invalid":"desktop-file-validate reports errors in a *.desktop file",
- "digest.partial":"Digest files do not contain all corresponding URI elements",
- "digest.assumed":"Existing digest must be assumed correct (Package level only)",
- "digestentry.unused":"Digest/Manifest entry has no matching SRC_URI entry",
- "digest.fail":"Digest does not match the specified local file",
- "digest.stray":"Digest files that do not have a corresponding ebuild",
- "digest.missing":"Digest files that are missing (ebuild exists, digest doesn't)",
- "digest.unmatch":"Digests which are incomplete (please check if your USE/ARCH includes all files)",
"ebuild.invalidname":"Ebuild files with a non-parseable or syntactically incorrect name (or using 2.1 versioning extensions)",
"ebuild.namenomatch":"Ebuild files that do not have the same name as their parent directory",
"changelog.missing":"Missing ChangeLog files",
"ebuild.allmasked",
"ebuild.nesteddie",
"desktop.invalid",
-"digest.assumed",
-"digest.missing",
-"digestentry.unused",
"DEPEND.badmasked","RDEPEND.badmasked","PDEPEND.badmasked",
"DEPEND.badindev","RDEPEND.badindev","PDEPEND.badindev",
"DEPEND.badmaskedindev","RDEPEND.badmaskedindev","PDEPEND.badmaskedindev",
logging.fatal("Couldn't read KEYWORDS from arch.list")
sys.exit(1)
-manifest1_compat = False
if portdir_overlay != portdir:
kwlist.update(portage.grabfile(
os.path.join(portdir_overlay, "profiles", "arch.list")))
has_filesdir = True
if not os.path.isdir(os.path.join(checkdir, "files")):
has_filesdir = False
- if manifest1_compat:
- stats["filedir.missing"] += 1
- fails["filedir.missing"].append(checkdir)
if isCvs:
try:
if os.path.exists(checkdir+"/files"):
filesdirlist=os.listdir(checkdir+"/files")
- if manifest1_compat:
- for y in filesdirlist:
- if not y.startswith("digest-"):
- continue
- relative_path = os.path.join(x, "files", y)
- full_path = os.path.join(repodir, relative_path)
- if stat.S_IMODE(os.stat(full_path).st_mode) & 0111:
- stats["file.executable"] += 1
- fails["file.executable"].append(x+"/files/"+y)
-
- mykey = catdir + "/" + y[7:]
- if y[7:] not in ebuildlist:
- #stray digest
- if options.mode == "fix":
- if options.pretend:
- print "(cd "+repodir+"/"+x+"/files; cvs rm -f "+y+")"
- else:
- os.system("(cd "+repodir+"/"+x+"/files; cvs rm -f "+y+")")
- else:
- stats["digest.stray"]=stats["digest.stray"]+1
- fails["digest.stray"].append(x+"/files/"+y)
- else:
- # We have an ebuild
- try:
- myuris, myfiles = portdb.getfetchlist(mykey, all=True)
- except portage.exception.InvalidDependString, e:
- # Already handled above.
- continue
-
- uri_dict = {}
- for myu in myuris:
- myubn = os.path.basename(myu)
- if myubn not in uri_dict:
- uri_dict[myubn] = [myu]
- else:
- uri_dict[myubn] += [myu]
-
- for myf in uri_dict:
- myff = repoman_settings["DISTDIR"] + "/" + myf
- if not mydigests.has_key(myf):
- uri_settings = portage.config(clone=repoman_settings)
- if options.mode == "fix":
- if not portage.fetch(uri_dict[myf], uri_settings):
- stats["digest.unmatch"] += 1
- fails["digest.unmatch"].append(y+"::"+myf)
- else:
- eb_name = portdb.findname2(mykey)[0]
- portage.doebuild(eb_name, "digest", "/",
- uri_settings, tree="porttree",
- mydbapi=portdb)
- else:
- stats["digest.partial"] += 1
- fails["digest.partial"].append(y+"::"+myf)
- elif "assume-digests" not in repoman_settings.features:
- if os.path.exists(myff):
- if not portage.checksum.verify_all(myff, mydigests[myf])[0]:
- stats["digest.fail"] += 1
- fails["digest.fail"].append(y+"::"+myf)
- elif repolevel == 3:
- stats["digest.assumed"] += 1
- fails["digest.assumed"].append(y+"::"+myf)
# recurse through files directory
# use filesdirlist as a stack, appending directories as needed so people can't hide > 20k files in a subdirectory.
if y in dadded:
stats["ebuild.disjointed"]=stats["ebuild.disjointed"]+1
fails["ebuild.disjointed"].append(x+"/"+y+".ebuild")
- if manifest1_compat and \
- not os.path.exists(os.path.join(checkdir, "files", "digest-"+y)):
- if options.mode == "fix":
- if options.pretend:
- print "You will need to run:"
- print " /usr/bin/ebuild "+repodir+"/"+x+"/"+y+".ebuild digest"
- else:
- retval=os.system("/usr/bin/ebuild "+repodir+"/"+x+"/"+y+".ebuild digest")
- if retval:
- print "!!! Exiting on ebuild digest (shell) error code:",retval
- sys.exit(retval)
- else:
- stats["digest.missing"]=stats["digest.missing"]+1
- fails["digest.missing"].append(x+"/files/digest-"+y)
myesplit=portage.pkgsplit(y)
if myesplit is None or myesplit[0] != x.split("/")[-1]:
stats["ebuild.invalidname"]=stats["ebuild.invalidname"]+1
if options.pretend:
print green("RepoMan sez:"), "\"So, you want to play it safe. Good call.\"\n"
- if fails["digest.missing"]:
- print green("Creating missing digests...")
- for x in fails["digest.missing"]:
- xs=x.split("/")
- del xs[-2]
- myeb="/".join(xs[:-1])+"/"+xs[-1][7:]
- if options.pretend:
- print "(ebuild "+portdir+"/"+myeb+".ebuild digest)"
- else:
- retval=os.system("ebuild "+portdir+"/"+myeb+".ebuild digest")
- if retval:
- print "!!! Exiting on ebuild digest (shell) error code:",retval
- sys.exit(retval)
-
mycvstree=portage.cvstree.getentries("./",recursive=1)
if isCvs and not mycvstree:
print "!!! It seems we don't have a cvs tree?"
myentry = Manifest2Entry(type=mytype, name=myname, hashes=myhashes)
return myentry
-def parseManifest1(mysplit):
- myentry = None
- if len(mysplit) == 4 and mysplit[0] in ["size"] + portage.const.MANIFEST1_HASH_FUNCTIONS:
- myname = mysplit[2]
- mytype = None
- mytype = guessManifestFileType(myname)
- if mytype == "AUX":
- if myname.startswith("files" + os.path.sep):
- myname = myname[6:]
- mysize = int(mysplit[3])
- myhashes = {mysplit[0]: mysplit[1]}
- myhashes["size"] = mysize
- myentry = Manifest1Entry(type=mytype, name=myname, hashes=myhashes)
- return myentry
-
class ManifestEntry(object):
__slots__ = ("type", "name", "hashes")
def __init__(self, **kwargs):
return 0
return 1
-class Manifest1Entry(ManifestEntry):
- def __str__(self):
- for hashkey in self.hashes:
- if hashkey != "size":
- break
- hashvalue = self.hashes[hashkey]
- myname = self.name
- if self.type == "AUX" and not myname.startswith("files" + os.sep):
- myname = os.path.join("files", myname)
- return " ".join([hashkey, str(hashvalue), myname, str(self.hashes["size"])])
-
class Manifest2Entry(ManifestEntry):
def __str__(self):
myline = " ".join([self.type, self.name, str(self.hashes["size"])])
return myline
class Manifest(object):
- parsers = (parseManifest2, parseManifest1)
+ parsers = (parseManifest2,)
def __init__(self, pkgdir, distdir, fetchlist_dict=None,
manifest1_compat=False, from_scratch=False):
""" create new Manifest instance for package in pkgdir
self.hashes = set()
self.hashes.update(portage.const.MANIFEST2_HASH_FUNCTIONS)
if manifest1_compat:
- self.hashes.update(portage.const.MANIFEST1_HASH_FUNCTIONS)
+ raise NotImplementedError("manifest1 support has been removed")
self.hashes.difference_update(hashname for hashname in \
list(self.hashes) if hashname not in hashfunc_map)
self.hashes.add("size")
if manifest1_compat:
- self.hashes.add(portage.const.MANIFEST1_REQUIRED_HASH)
+ raise NotImplementedError("manifest1 support has been removed")
self.hashes.add(portage.const.MANIFEST2_REQUIRED_HASH)
for t in portage.const.MANIFEST2_IDENTIFIERS:
self.fhashdict[t] = {}
- self.compat = manifest1_compat
if not from_scratch:
self._read()
if fetchlist_dict != None:
""" Similar to getDigests(), but restricted to files of the given type. """
return self.fhashdict[ftype]
- def _readDigests(self, myhashdict=None):
- """ Parse old style digest files for this Manifest instance """
- if myhashdict is None:
- myhashdict = {}
- try:
- for d in os.listdir(os.path.join(self.pkgdir, "files")):
- if d.startswith("digest-"):
- self._readManifest(os.path.join(self.pkgdir, "files", d), mytype="DIST",
- myhashdict=myhashdict)
- except (IOError, OSError), e:
- if e.errno == errno.ENOENT:
- pass
- else:
- raise
- return myhashdict
-
def _readManifest(self, file_path, myhashdict=None, **kwargs):
- """Parse a manifest or an old style digest. If myhashdict is given
- then data will be added too it. Otherwise, a new dict will be created
- and returned."""
+ """Parse a manifest. If myhashdict is given then data will be added too it.
+ Otherwise, a new dict will be created and returned."""
try:
fd = open(file_path, "r")
if myhashdict is None:
self._readManifest(self.getFullname(), myhashdict=self.fhashdict)
except FileNotFound:
pass
- if self.compat:
- self._readDigests(myhashdict=self.fhashdict)
def _parseManifestLines(self, mylines):
"""Parse manifest lines and return a list of manifest entries."""
myhashdict[myentry_type][myentry.name].update(myentry.hashes)
return myhashdict
- def _writeDigests(self, force=False):
- """ Create old style digest files for this Manifest instance """
- cpvlist = [os.path.join(self._pkgdir_category(), x[:-7]) for x in os.listdir(self.pkgdir) if x.endswith(".ebuild")]
- rval = []
- try:
- os.makedirs(os.path.join(self.pkgdir, "files"))
- except OSError, oe:
- if oe.errno == errno.EEXIST:
- pass
- else:
- raise
- for cpv in cpvlist:
- dname = os.path.join(self.pkgdir, "files", "digest-%s" % self._catsplit(cpv)[1])
- distlist = self._getCpvDistfiles(cpv)
- missing_digests = set()
- for f in distlist:
- if f not in self.fhashdict["DIST"] or len(self.fhashdict["DIST"][f]) == 0:
- missing_digests.add(f)
- if missing_digests:
- # This allows us to force remove of stale digests for the
- # ebuild --force digest option.
- distlist = [f for f in distlist if f not in missing_digests]
- update_digest = True
- if not force:
- try:
- f = open(dname, "r")
- old_data = self._parseDigests(f)
- f.close()
- new_data = self._getDigestData(distlist)
- if not old_data and not new_data:
- # SRC_URI is empty
- update_digest = False
- elif len(old_data) == 1 and "DIST" in old_data:
- if "DIST" in new_data:
- for myfile in new_data["DIST"]:
- for hashname in \
- new_data["DIST"][myfile].keys():
- if hashname != "size" and hashname not in \
- portage.const.MANIFEST1_HASH_FUNCTIONS:
- del new_data["DIST"][myfile][hashname]
- if new_data["DIST"] == old_data["DIST"]:
- update_digest = False
- except (IOError, OSError), e:
- if errno.ENOENT == e.errno:
- pass
- else:
- raise
- if update_digest:
- mylines = self._createDigestLines1(distlist, self.fhashdict)
- if mylines:
- mylines = "\n".join(mylines) + "\n"
- else:
- mylines = ""
- write_atomic(dname, mylines)
- rval.append(dname)
- return rval
-
def _getDigestData(self, distlist):
"""create a hash dict for a specific list of files"""
myhashdict = {}
myhashdict[mytype][myname].update(self.fhashdict[mytype][myname])
return myhashdict
- def _createDigestLines1(self, distlist, myhashdict):
- """ Create an old style digest file."""
- mylines = []
- myfiles = myhashdict["DIST"].keys()
- myfiles.sort()
- for f in myfiles:
- if f in distlist:
- myhashkeys = myhashdict["DIST"][f].keys()
- myhashkeys.sort()
- for h in myhashkeys:
- if h not in portage.const.MANIFEST1_HASH_FUNCTIONS:
- continue
- myline = " ".join([h, str(myhashdict["DIST"][f][h]), f, str(myhashdict["DIST"][f]["size"])])
- mylines.append(myline)
- return mylines
-
- def _addDigestsToManifest(self, digests, fd):
- """ Add entries for old style digest files to Manifest file """
- mylines = []
- for dname in digests:
- myhashes = perform_multiple_checksums(dname, portage.const.MANIFEST1_HASH_FUNCTIONS+["size"])
- for h in myhashes:
- mylines.append((" ".join([h, str(myhashes[h]), os.path.join("files", os.path.basename(dname)), str(myhashes["size"])])))
- fd.write("\n".join(mylines))
- fd.write("\n")
-
def _createManifestEntries(self):
mytypes = self.fhashdict.keys()
mytypes.sort()
if h not in ["size"] + portage.const.MANIFEST2_HASH_FUNCTIONS:
del myentry.hashes[h]
yield myentry
- if self.compat and t != "DIST":
- mysize = self.fhashdict[t][f]["size"]
- myhashes = self.fhashdict[t][f]
- for h in myhashkeys:
- if h not in portage.const.MANIFEST1_HASH_FUNCTIONS:
- continue
- yield Manifest1Entry(
- type=t, name=f, hashes={"size":mysize, h:myhashes[h]})
-
- if self.compat:
- cvp_list = self.fetchlist_dict.keys()
- cvp_list.sort()
- manifest1_hashes = set(hashname for hashname in \
- portage.const.MANIFEST1_HASH_FUNCTIONS \
- if hashname in hashfunc_map)
- manifest1_hashes.add(portage.const.MANIFEST1_REQUIRED_HASH)
- manifest1_hashes.add("size")
- for cpv in cvp_list:
- digest_path = os.path.join("files", "digest-%s" % self._catsplit(cpv)[1])
- dname = os.path.join(self.pkgdir, digest_path)
- try:
- myhashes = perform_multiple_checksums(dname, manifest1_hashes)
- myhashkeys = myhashes.keys()
- myhashkeys.sort()
- for h in myhashkeys:
- if h in portage.const.MANIFEST1_HASH_FUNCTIONS:
- yield Manifest1Entry(type="AUX", name=digest_path,
- hashes={"size":myhashes["size"], h:myhashes[h]})
- except FileNotFound:
- pass
def checkIntegrity(self):
for t in self.fhashdict:
""" Write Manifest instance to disk, optionally signing it """
self.checkIntegrity()
try:
- if self.compat:
- self._writeDigests()
myentries = list(self._createManifestEntries())
update_manifest = True
if not force:
distfilehashes = {}
self.__init__(self.pkgdir, self.distdir,
fetchlist_dict=self.fetchlist_dict, from_scratch=True,
- manifest1_compat=self.compat)
+ manifest1_compat=False)
cpvlist = []
pn = os.path.basename(self.pkgdir.rstrip(os.path.sep))
cat = self._pkgdir_category()