Update to most recent versions and add changes from djanderson
authorfuzzyray <fuzzyray@gentoo.org>
Tue, 5 May 2009 21:04:27 +0000 (21:04 -0000)
committerfuzzyray <fuzzyray@gentoo.org>
Tue, 5 May 2009 21:04:27 +0000 (21:04 -0000)
svn path=/trunk/gentoolkit/; revision=599

bin/eclean
bin/euse
bin/glsa-check
bin/revdep-rebuild
pym/gentoolkit/helpers2.py
pym/gentoolkit/package.py

index 8b473f96b0af659b68d2e3a4d82f1622bcea99a8..5497cf39cd3d061ea10c9b18af7fa3c818cb5fcf 100644 (file)
@@ -1,8 +1,9 @@
-#!/usr/bin/env python
+#!/usr/bin/python
 # Copyright 2003-2005 Gentoo Foundation
 # Distributed under the terms of the GNU General Public License v2
 # $Header: $
 
+from __future__ import with_statement
 
 ###############################################################################
 # Meta:
@@ -15,6 +16,7 @@ __description__ = "A cleaning tool for Gentoo distfiles and binaries."
 
 ###############################################################################
 # Python imports:
+
 import sys
 import os, stat
 import re
@@ -502,12 +504,13 @@ def exclDictMatch(excl_dict,pkg):
 # findDistfiles: find all obsolete distfiles.
 # XXX: what about cvs ebuilds? i should install some to see where it goes...
 def findDistfiles( \
+               myoptions, \
                exclude_dict={}, \
                destructive=False,\
                fetch_restricted=False, \
                package_names=False, \
                time_limit=0, \
-               size_limit=0):
+               size_limit=0,):
        # this regexp extracts files names from SRC_URI. It is not very precise,
        # but we don't care (may return empty strings, etc.), since it is fast.
        file_regexp = re.compile('([a-zA-Z0-9_,\.\-\+\~]*)[\s\)]')
@@ -548,7 +551,12 @@ def findDistfiles( \
                        except KeyError: continue
                del pkg_list
 
-       # create a dictionary of files which should be deleted 
+       # create a dictionary of files which should be deleted
+       if not (os.path.isdir(distdir)):
+               eerror("%s does not appear to be a directory." % distdir, myoptions['nocolor'])
+               eerror("Please set DISTDIR to a sane value.", myoptions['nocolor'])
+               eerror("(Check your /etc/make.conf and environment).", myoptions['nocolor'])
+               exit(1)
        for file in os.listdir(distdir):
                filepath = os.path.join(distdir, file)
                try: file_stat = os.stat(filepath)
@@ -589,12 +597,19 @@ def findDistfiles( \
 # XXX: packages are found only by symlinks. Maybe i should also return .tbz2
 #      files from All/ that have no corresponding symlinks.
 def findPackages( \
+               myoptions, \
                exclude_dict={}, \
                destructive=False, \
                time_limit=0, \
                package_names=False):
        clean_dict = {}
-       # create a full package dictionnary
+       # create a full package dictionary
+       
+       if not (os.path.isdir(pkgdir)):
+               eerror("%s does not appear to be a directory." % pkgdir, myoptions['nocolor'])
+               eerror("Please set PKGDIR to a sane value.", myoptions['nocolor'])
+               eerror("(Check your /etc/make.conf and environment).", myoptions['nocolor'])
+               exit(1)
        for root, dirs, files in os.walk(pkgdir):
                if root[-3:] == 'All': continue
                for file in files:
@@ -631,7 +646,7 @@ def findPackages( \
                        del clean_dict[mycpv]
                        continue
                if portage.cpv_getkey(mycpv) in cp_all:
-                       # exlusion because of --package-names 
+                       # exlusion because of --package-names
                        del clean_dict[mycpv]
 
        return clean_dict
@@ -673,7 +688,12 @@ def doCleanup(clean_dict,action,myoptions):
                                       "Do you want to delete this " \
                                       + file_type+"?"):
                        # non-interactive mode or positive answer. 
-                       # For each file,...
+                       # For each file, try to delete the file and clean it out
+                       # of Packages metadata file
+                       if action == 'packages':
+                               metadata = portage.getbinpkg.PackageIndex()
+                               with open(os.path.join(pkgdir, 'Packages')) as metadata_file:
+                                       metadata.read(metadata_file)
                        for file in clean_dict[mykey]:
                                # ...get its size...
                                filesize = 0
@@ -683,11 +703,21 @@ def doCleanup(clean_dict,action,myoptions):
                                        except: eerror("Could not read size of "\
                                                       +file, myoptions['nocolor'])
                                # ...and try to delete it.
-                               try: os.unlink(file)
-                               except: eerror("Could not delete "+file, \
-                                              myoptions['nocolor'])
+                               try:
+                                       os.unlink(file)
+                               except:
+                                       eerror("Could not delete "+file, \
+                                        myoptions['nocolor'])
                                # only count size if successfully deleted
-                               else: clean_size += filesize
+                               else:
+                                       clean_size += filesize
+                                       if action == 'packages':
+                                               metadata.packages[:] = [p for p in metadata.packages if 'CPV' in p and p['CPV'] != file]
+                               
+                       if action == 'packages':
+                               with open(os.path.join(pkgdir, 'Packages'), 'w') as metadata_file:
+                                       metadata.write(metadata_file)
+
        # return total size of deleted or to delete files
        return clean_size
 
@@ -704,13 +734,15 @@ def doAction(action,myoptions,exclude_dict={}):
                einfo("Building file list for "+action+" cleaning...", \
                      myoptions['nocolor'])
        if action == 'packages':
-               clean_dict = findPackages( \
+               clean_dict = findPackages(
+                       myoptions, \
                        exclude_dict=exclude_dict, \
                        destructive=myoptions['destructive'], \
                        package_names=myoptions['package-names'], \
                        time_limit=myoptions['time-limit'])
        else: 
                clean_dict = findDistfiles( \
+                       myoptions, \
                        exclude_dict=exclude_dict, \
                        destructive=myoptions['destructive'], \
                        fetch_restricted=myoptions['fetch-restricted'], \
index b49b120ebd412598fa56fecfe45eab0e696a3e5a..df61e32bfb9aa9b066a8088d6f703add4e6f0358 100755 (executable)
--- a/bin/euse
+++ b/bin/euse
@@ -346,7 +346,7 @@ showinstdesc() {
        local current_desc
        local args
        local -i foundone=0
-       local IFS
+       local OIFS="$IFS"
 
        args=("${@:-*}")
 
@@ -376,7 +376,7 @@ showinstdesc() {
                                        echo "$desc"
                                        # get list of installed packages matching this USE flag.
                                        IFS=$'\n'
-                                       packages=($(equery -q -C hasuse -i "${1}" | awk '{ print $(NF-1) }'))
+                                       packages=($(equery -q -C hasuse -i "${1}" | awk '{ print $(NF-1) }' | sort))
                                        foundone+=${#packages[@]}
                                        printf "\nInstalled packages matching this USE flag: "
                                        if [ ${foundone} -gt 0 ]; then
@@ -396,7 +396,9 @@ showinstdesc() {
                                        #       exit status of equery instead of a subshell and pipe to wc -l
                                        if [ $(equery -q -C list -i -e "${pkg}" | wc -l) -gt 0 ]; then
                                                foundone=1
+                                               IFS="$OIFS"
                                                get_flagstatus "${flag}"
+                                               IFS=': '
                                                printf "%s (%s):\n%s\n\n" "${flag}" "${pkg}" "${desc#- }"
                                        fi
                                done < <(grep ":${1}  *-" "${descdir}/use.local.desc")
@@ -408,6 +410,7 @@ showinstdesc() {
        if [ ${foundone} -lt 1 ]; then
                echo "no matching entries found"
        fi
+       IFS="$OIFS"
 }
 
 # show a list of all currently active flags and where they are activated
index 1fb577d8af761eae2a19019be95ae14de0c2557e..0ce133e34aead1eec83562233f2e9cafce666350 100644 (file)
@@ -16,7 +16,7 @@ try:
 except ImportError:
        from output import *
 
-from getopt import getopt,GetoptError
+from getopt import getopt, GetoptError
 
 __program__ = "glsa-check"
 __author__ = "Marius Mauch <genone@gentoo.org>"
@@ -81,10 +81,10 @@ try:
        # sanity checking
        if len(args) <= 0:
                sys.stderr.write("no option given: what should I do ?\n")
-               mode="help"
+               mode = "HELP"
        elif len(args) > 1:
                sys.stderr.write("please use only one command per call\n")
-               mode = "help"
+               mode = "HELP"
        else:
                # in what mode are we ?
                args = args[0]
@@ -95,32 +95,37 @@ try:
 except GetoptError, e:
        sys.stderr.write("unknown option given: ")
        sys.stderr.write(str(e)+"\n")
-       mode = "help"
+       mode = "HELP"
 
 # we need a set of glsa for most operation modes
 if len(params) <= 0 and mode in ["fix", "test", "pretend", "dump", "inject", "mail"]:
        sys.stderr.write("\nno GLSA given, so we'll do nothing for now. \n")
        sys.stderr.write("If you want to run on all GLSA please tell me so \n")
        sys.stderr.write("(specify \"all\" as parameter)\n\n")
-       mode = "help"
+       mode = "HELP"
 elif len(params) <= 0 and mode == "list":
        params.append("new")
        
 # show help message
-if mode == "help":
-       sys.stderr.write("\nSyntax: glsa-check <option> [glsa-list]\n\n")
+if mode == "help" or mode == "HELP":
+       msg = "Syntax: glsa-check <option> [glsa-list]\n\n"
        for m in optionmap:
-               sys.stderr.write(m[0] + "\t" + m[1] + "   \t: " + m[-1] + "\n")
+               msg += m[0] + "\t" + m[1] + "   \t: " + m[-1] + "\n"
                for o in m[2:-1]:
-                       sys.stderr.write("\t" + o + "\n")
-       sys.stderr.write("\nglsa-list can contain an arbitrary number of GLSA ids, \n")
-       sys.stderr.write("filenames containing GLSAs or the special identifiers \n")
-       sys.stderr.write("'all', 'new' and 'affected'\n")
-       sys.exit(1)
+                       msg += "\t" + o + "\n"
+       msg += "\nglsa-list can contain an arbitrary number of GLSA ids, \n"
+       msg += "filenames containing GLSAs or the special identifiers \n"
+       msg += "'all', 'new' and 'affected'\n"
+       if mode == "help":
+               sys.stdout.write(msg)
+               sys.exit(0)
+       else:
+               sys.stderr.write("\n" + msg)
+               sys.exit(1)
 
 # we need root priviledges for write access
 if mode in ["fix", "inject"] and os.geteuid() != 0:
-       sys.stderr.write("\nThis tool needs root access to "+mode+" this GLSA\n\n")
+       sys.stderr.write(__program__ + ": root access is needed for \""+mode+"\" mode\n")
        sys.exit(2)
 
 # show version and copyright information
@@ -219,7 +224,7 @@ def summarylist(myglsalist, fd1=sys.stdout, fd2=sys.stderr):
                                fd1.write("... ")
                else:
                        for pkg in myglsa.packages.keys():
-                               mylist = vardb.match(portage.dep_getkey(pkg))
+                               mylist = vardb.match(portage.dep_getkey(str(pkg)))
                                if len(mylist) > 0:
                                        pkg = color(" ".join(mylist))
                                fd1.write(" " + pkg + " ")
@@ -227,7 +232,7 @@ def summarylist(myglsalist, fd1=sys.stdout, fd2=sys.stderr):
                fd1.write(")")
                if list_cve:
                        fd1.write(" "+(",".join([r[:13] for r in myglsa.references if r[:4] in ["CAN-", "CVE-"]])))
-               fd1.write("\n")         
+               fd1.write("\n")
        return 0
 
 if mode == "list":
@@ -261,6 +266,8 @@ if mode in ["dump", "fix", "inject", "pretend"]:
                                        exitcode >>= 8
                                if exitcode:
                                        sys.exit(exitcode)
+                       if len(mergelist):
+                               sys.stdout.write("\n")
                        myglsa.inject()
                elif mode == "pretend":
                        sys.stdout.write("Checking GLSA "+myid+"\n")
@@ -278,10 +285,10 @@ if mode in ["dump", "fix", "inject", "pretend"]:
                                        sys.stdout.write("     " + pkg + " (" + oldver + ")\n")
                        else:
                                sys.stdout.write("Nothing to do for this GLSA\n")
+                       sys.stdout.write("\n")
                elif mode == "inject":
                        sys.stdout.write("injecting " + myid + "\n")
                        myglsa.inject()
-               sys.stdout.write("\n")
        sys.exit(0)
 
 # test is a bit different as Glsa.test() produces no output
@@ -323,12 +330,12 @@ if mode == "mail":
        # color doesn't make any sense for mail
        nocolor()
 
-       if glsaconfig.has_key("PORTAGE_ELOG_MAILURI"):
+       if "PORTAGE_ELOG_MAILURI" in glsaconfig:
                myrecipient = glsaconfig["PORTAGE_ELOG_MAILURI"].split()[0]
        else:
                myrecipient = "root@localhost"
        
-       if glsaconfig.has_key("PORTAGE_ELOG_MAILFROM"):
+       if "PORTAGE_ELOG_MAILFROM" in glsaconfig:
                myfrom = glsaconfig["PORTAGE_ELOG_MAILFROM"]
        else:
                myfrom = "glsa-check"
index fac03d876a6cd27e34da2aadef4c163599b0ce4d..72efba0132f244dd80fca827df8d0630e9134ae1 100755 (executable)
@@ -123,6 +123,7 @@ rm() {
        eerror "I was instructed to rm '$@'"
        die 1 "Refusing to delete anything before changing to temporary directory."
 }
+: <<'EW'
 ##
 # GNU find has -executable, but if our users' finds do not have that flag
 # we emulate it with this function. Also emulates -writable and -readable.
@@ -158,6 +159,7 @@ find() {
        fi
        find "$@"
 }
+EW
 
 print_usage() {
 cat << EOF
@@ -222,7 +224,7 @@ countdown() {
 # Replace whitespace with linebreaks, normalize repeated '/' chars, and sort -u
 # (If any libs have whitespace in their filenames, someone needs punishment.)
 clean_var() {
-       awk 'BEGIN         {RS="[[:space:]]"}
+       gawk 'BEGIN         {RS="[[:space:]]"}
             /-\*/         {exit}
             /[^[:space:]]/ {gsub(/\/\/+/, "/"); print}' | sort -u
 }
@@ -633,8 +635,8 @@ get_files() {
                        findMask="${findMask[@]/#/-o -path }"
                        findMask="( ${findMask#-o } ) -prune -o"
                fi
-               # TODO: Check this
-               find ${SEARCH_DIRS[@]} $findMask -type f \( -executable -o \
+               # TODO: Check this -- afaict SEARCH_DIRS isn't an array, so this should just be $SEARCH_DIRS?
+               find ${SEARCH_DIRS[@]} $findMask -type f \( -perm -u+x -o -perm -g+x -o -perm -o+x -o \
                        -name '*.so' -o -name '*.so.*' -o -name '*.la' \) -print 2> /dev/null |
                        sort -u > "$FILES_FILE" ||
                        die $? "find failed to list binary files (This is a bug.)"
@@ -735,18 +737,39 @@ main_checks() {
                                fi
                        elif [[ $SEARCH_BROKEN ]]; then
                                # Look for broken .la files
+                               la_SEARCH_DIRS="$SEARCH_DIRS"
+                               la_search_dir=""
+                               la_broken=""
+                               la_lib=""
                                for depend in $(
-                                       awk -F"[=']" '/^dependency_libs/{
-                                               gsub("^-[^[:space:]]*", "", $3);
-                                               gsub("[[:space:]]-[^[:space:]]*", "", $3);
+                                       gawk -F"[=']" '/^dependency_libs/{
                                                print $3
                                        }' "$target_file"
                                ); do
                                        if [[ $depend = /* && ! -e $depend ]]; then
                                                echo "obj $target_file" >> "$BROKEN_FILE"
                                                echo_v "  broken $target_file (requires $depend)"
+                                       elif [[ $depend = -[LR]/* ]]; then
+                                               if ! [[ $'\n'${la_SEARCH_DIRS}$'\n' == *$'\n'${depend#-?}$'\n'* ]]; then
+                                                       la_SEARCH_DIRS+=$'\n'"${depend#-?}"
+                                               fi
+                                       elif [[ $depend = "-l"* ]]; then
+                                               la_lib="lib${depend#-l}"
+                                               la_broken="yes"
+                                               IFS=$'\n'
+                                               for la_search_dir in $la_SEARCH_DIRS; do
+                                                       if [[ -e ${la_search_dir}/${la_lib}.so || -e ${la_search_dir}/${la_lib}.a ]]; then
+                                                               la_broken="no"
+                                                       fi
+                                               done
+                                               IFS="$OIFS"
+                                               if [[ $la_broken = yes ]]; then
+                                                       echo "obj $target_file" >> "$BROKEN_FILE"
+                                                       echo_v "  broken $target_file (requires $depend)"
+                                               fi
                                        fi
                                done
+                               unset la_SEARCH_DIRS la_search_dir la_broken la_lib
                        fi
                        [[ $VERBOSE ]] &&
                                progress $((++i)) $numFiles $target_file ||
@@ -760,7 +783,7 @@ main_checks() {
                        done < <(
                                # Regexify LD_LIBRARY_MASK. Exclude it from the search.
                                LD_LIBRARY_MASK="${LD_LIBRARY_MASK//$'\n'/|}"
-                               awk -v ldmask="(${LD_LIBRARY_MASK//./\\\.})" '
+                               gawk -v ldmask="(${LD_LIBRARY_MASK//./\\\.})" '
                                        /no version information available/ && $0 !~ ldmask {
                                                gsub(/[()]/, "", $NF)
                                                if (seen[$NF]++)  next
@@ -945,7 +968,7 @@ show_unowned_files() {
                ewarn "The broken files are:"
                while read filename junk; do
                        [[ $junk = *none* ]] && ewarn "  $filename"
-               done < "$OWNERS_FILE" | awk '!s[$0]++' # (omit dupes)
+               done < "$OWNERS_FILE" | gawk '!s[$0]++' # (omit dupes)
        fi
 }
 ##
@@ -1080,8 +1103,11 @@ cleanup() {
                einfo 'Build finished correctly. Removing temporary files...'
                einfo
                einfo 'You can re-run revdep-rebuild to verify that all libraries and binaries'
-               einfo 'are fixed. If some inconsistency remains, it can be orphaned file, deep'
-               einfo 'dependency, binary package or specially evaluated library.'
+               einfo 'are fixed. Possible reasons for remaining inconsistencies include:'
+               einfo '  orphaned files'
+               einfo '  deep dependencies'
+               einfo "  packages installed outside of portage's control"
+               einfo '  specially-evaluated libraries'
                if [[ -r "$OWNERS_FILE" && -s "$OWNERS_FILE" ]]; then
                        show_unowned_files
                fi
index 20d1de092f242e7c5e990cf6840c1f6f691ddf0a..1a2530a0c05ccd210aca226a391118d0ddb15d26 100644 (file)
@@ -132,6 +132,8 @@ def uses_globbing(query):
 def _do_complex_lookup(query, query_opts):
        """Find matches for a query which is a regex or includes globbing."""
 
+       # pylint: Too many branches (18/12)
+       # pylint: disable-message=R0912
        result = []
 
        if query_opts["includeInstalled"]:
@@ -240,8 +242,6 @@ def _do_simple_lookup(query, query_opts):
 def do_lookup(query, query_opts):
        """A high-level wrapper around gentoolkit package-finder functions.
 
-       @todo: equery modules to move to do_lookup: c,m,u,w
-
        @type query: str
        @param query: pkg, cat/pkg, pkg-ver, cat/pkg-ver, atom or regex
        @type query_opts: dict
@@ -401,9 +401,9 @@ def prepare_categories(category_filter):
 
 
 def split_query(query):
-       """Split a query, using either.
+       """Split a query into category, name, version and revision.
 
-       @see: split_atom, gentoolkit.split_package_name
+       @type query: str
        @param query: pkg, cat/pkg, pkg-ver, cat/pkg-ver, atom or regex
        @rtype: tuple
        @return: (category, pkg_name, version, revision)
index 65cdb9a94dfd3b64031a20162e670f8ec5545a6d..340a512376fd00dc10a8f4819488b8ee32885b7c 100644 (file)
@@ -465,7 +465,7 @@ class Package(object):
                """
                if not self._db:
                        self._db = portage.dblink(
-                               category,
+                               self.category,
                                "%s-%s" % (self.name, self.fullversion),
                                settings["ROOT"],
                                settings