poky/scripts/pstage-scanner
Joshua Lock 971907567c Enable build dir outside of the poky directory
You need to first set up the build directory by sourcing the poky build script,
after that builds can be run in that directory so long as bitbake is in $PATH
removing the need to source the init script for each build.

i.e:
$ . poky-init-build-env ~/my-build
$ bitbake some-image
<<later, in a different shell>>
$ cd ~/my-build
$ export PATH=/path/to/bitbake/bin:$PATH
$ bitbake an-image

This patch also removes use of OEROOT in recipes, etc.

Signed-off-by: Joshua Lock <josh@linux.intel.com>
2010-07-21 15:39:53 +01:00

4.4 KiB
Executable File

#!/usr/bin/env python

This script will scan all of the packages in PSTAGE_DIR (or argv[1])

in search of packages which install files outside of their native sysroot

import os, sys, tarfile, shutil import subprocess as sub

logf = "" pcount = 0 ecount = 0

def main(): """Generate a list of pstage packages and scan them for badness""" package_list = []

try:
    path = sysv.arg[1]
except:
    # Assume pstage is a child of tmp, Poky's default
    tmpdir = None
    sub.Popen(["bitbake", "-e"], stdout=sub.PIPE,stderr=sub.PIPE)
    err, out = p.communicate()
    if (!out):
        print("bitbake not in your environment, try pstage-scanner /some/path/to/pstage")
        exit
    for line in out:
        if line.find("PSTAGE_DIR=") != -1:
            tmpdir = line.partition("=")[2].strip("\"")
            break

if len(path) < 1 or not os.path.exists(path):
    print ("No path defined and bitbake not in your environment, try pstage-scanner /some/path/to/pstage")
    exit

global logf
try:
    logf = sys.argv[2]
except:
    logf = os.path.join(path, "pstage-scanner.log")

## Create a working directory
tempdir = os.path.join(path, "tmp")
os.mkdir(tempdir)

## Iterate each child of the target directory looking for .ipk files and
## building a list of files to process
for root, dirs, files in os.walk(path):
    for d in dirs:
        for f in os.listdir(os.path.join(root,d)):
            if os.path.splitext(f)[1] == ".ipk" and f.find("native") == -1 and f.find("cross") == -1:
                package_list.append(os.path.join(root,d,f))

## Next we iterate our built list of files and process each package
for pkg in package_list:
    tmp = os.path.join(tempdir, os.path.splitext(os.path.split(pkg)[1])[0])
    os.mkdir(tmp)
    scan_package(pkg, tmp)

## Tidy up working directory
shutil.rmtree(tempdir)

## Report a summary
log("Finished scanning packaged staging. Scanned %i packages with %i errors" % (pcount, ecount))

def scan_package(filepath, parentdir): """Helper method to do bookkeeping, passes all installable directories to scan_dir which does the actual scanning.""" os.chdir(parentdir)

## increment the package count, for the summary
global pcount
pcount += 1

## An ipk file is an ar archive containing two gzipped tarball directories
## data.tar.gz is inflated to / and contains the actual files
## control.tar.gz is metadata and scripts for the package
## The archive also contains a file, debian binary, which is unused
## Python can't handle ar archives ootb. So we cheat and inflate with
## the ar program on the host
sub.call(["ar", "x", filepath])

## The things we care about are in data.tar.gz
tgz = tarfile.open(os.path.join(parentdir, "data.tar.gz"))
dest = os.path.join(parentdir, "inflate")
os.mkdir(dest)
tgz.extractall(dest)

## We want to know the target arch so that we can ensure the package is
## only installing into its target sysroot
arch =  os.path.splitext(os.path.basename(filepath))[0].split("_")[-1]
if arch == "64":
    arch = "x86_64"

## The ignored list contains directories we don't care to scan
ignored = ["pkgdata", "stamps", "deploy"]

## Scan the package for badness
pname = os.path.split(filepath)[1]
for di in os.listdir(dest):
    if di not in ignored:
        scan_dir(os.path.join(dest, di), arch, pname)

def scan_dir (directory, arch, package_name): """Scan the contents of directory for things installing outside of native sysroot"""

global ecount
msg = ""

head, tail = os.path.split(directory)
if not tail == "sysroots":
    msg += "Tsk tsk, installing to " + tail + "\n"
    for d in os.listdir(directory):
        msg += "Installing %s in %s" % (d, tail) + "\n"
        ecount += 1
else:
    for d in os.listdir(directory):
        if not d.startswith(arch) and d.find("fixmepath") == -1:
            msg += "Tsk tsk, installing into non-native sysroot " + os.path.join(directory, d)
            ecount += 1

if len(msg) > 0:
    log("Scanning package " + package_name  + "\n" + msg)

def log (message): global logf logfile = open (logf, 'a+') logfile.write(message + "\n") print "LOG: " + message logfile.close()

if name == "main": main()