summaryrefslogtreecommitdiff
path: root/classes/base.bbclass
diff options
context:
space:
mode:
Diffstat (limited to 'classes/base.bbclass')
-rw-r--r--classes/base.bbclass957
1 files changed, 766 insertions, 191 deletions
diff --git a/classes/base.bbclass b/classes/base.bbclass
index 249a25a218..e6cfeccc46 100644
--- a/classes/base.bbclass
+++ b/classes/base.bbclass
@@ -1,23 +1,190 @@
-BB_DEFAULT_TASK = "build"
+BB_DEFAULT_TASK ?= "build"
+
+# like os.path.join but doesn't treat absolute RHS specially
+def base_path_join(a, *p):
+ path = a
+ for b in p:
+ if path == '' or path.endswith('/'):
+ path += b
+ else:
+ path += '/' + b
+ return path
+
+def base_path_relative(src, dest):
+ """ Return a relative path from src to dest.
+
+ >>> base_path_relative("/usr/bin", "/tmp/foo/bar")
+ ../../tmp/foo/bar
+
+ >>> base_path_relative("/usr/bin", "/usr/lib")
+ ../lib
+
+ >>> base_path_relative("/tmp", "/tmp/foo/bar")
+ foo/bar
+ """
+ from os.path import sep, pardir, normpath, commonprefix
+
+ destlist = normpath(dest).split(sep)
+ srclist = normpath(src).split(sep)
+
+ # Find common section of the path
+ common = commonprefix([destlist, srclist])
+ commonlen = len(common)
+
+ # Climb back to the point where they differentiate
+ relpath = [ pardir ] * (len(srclist) - commonlen)
+ if commonlen < len(destlist):
+ # Add remaining portion
+ relpath += destlist[commonlen:]
+
+ return sep.join(relpath)
+
+def base_path_out(path, d):
+ """ Prepare a path for display to the user. """
+ rel = base_path_relative(d.getVar("TOPDIR", 1), path)
+ if len(rel) > len(path):
+ return path
+ else:
+ return rel
+
+# for MD5/SHA handling
+def base_chk_load_parser(config_paths):
+ import ConfigParser
+ parser = ConfigParser.ConfigParser()
+ if len(parser.read(config_paths)) < 1:
+ raise ValueError("no ini files could be found")
+
+ return parser
+
+def base_chk_file_vars(parser, localpath, params, data):
+ try:
+ name = params["name"]
+ except KeyError:
+ return False
+ flagName = "%s.md5sum" % name
+ want_md5sum = bb.data.getVarFlag("SRC_URI", flagName, data)
+ flagName = "%s.sha256sum" % name
+ want_sha256sum = bb.data.getVarFlag("SRC_URI", flagName, data)
+
+ if (want_sha256sum == None and want_md5sum == None):
+ # no checksums to check, nothing to do
+ return False
+
+ if not os.path.exists(localpath):
+ localpath = base_path_out(localpath, data)
+ bb.note("The localpath does not exist '%s'" % localpath)
+ raise Exception("The path does not exist '%s'" % localpath)
+
+ if want_md5sum:
+ try:
+ md5pipe = os.popen('PATH=%s md5sum %s' % (bb.data.getVar('PATH', data, True), localpath))
+ md5data = (md5pipe.readline().split() or [ "" ])[0]
+ md5pipe.close()
+ except OSError, e:
+ raise Exception("Executing md5sum failed")
+ if want_md5sum != md5data:
+ bb.note("The MD5Sums did not match. Wanted: '%s' and Got: '%s'" % (want_md5sum, md5data))
+ raise Exception("MD5 Sums do not match. Wanted: '%s' Got: '%s'" % (want_md5sum, md5data))
+
+ if want_sha256sum:
+ try:
+ shapipe = os.popen('PATH=%s oe_sha256sum %s' % (bb.data.getVar('PATH', data, True), localpath))
+ sha256data = (shapipe.readline().split() or [ "" ])[0]
+ shapipe.close()
+ except OSError, e:
+ raise Exception("Executing shasum failed")
+ if want_sha256sum != sha256data:
+ bb.note("The SHA256Sums did not match. Wanted: '%s' and Got: '%s'" % (want_sha256sum, sha256data))
+ raise Exception("SHA256 Sums do not match. Wanted: '%s' Got: '%s'" % (want_sha256sum, sha256data))
+
+ return True
+
+
+def base_chk_file(parser, pn, pv, src_uri, localpath, data):
+ no_checksum = False
+ # Try PN-PV-SRC_URI first and then try PN-SRC_URI
+ # we rely on the get method to create errors
+ pn_pv_src = "%s-%s-%s" % (pn,pv,src_uri)
+ pn_src = "%s-%s" % (pn,src_uri)
+ if parser.has_section(pn_pv_src):
+ md5 = parser.get(pn_pv_src, "md5")
+ sha256 = parser.get(pn_pv_src, "sha256")
+ elif parser.has_section(pn_src):
+ md5 = parser.get(pn_src, "md5")
+ sha256 = parser.get(pn_src, "sha256")
+ elif parser.has_section(src_uri):
+ md5 = parser.get(src_uri, "md5")
+ sha256 = parser.get(src_uri, "sha256")
+ else:
+ no_checksum = True
+
+ # md5 and sha256 should be valid now
+ if not os.path.exists(localpath):
+ localpath = base_path_out(localpath, data)
+ bb.note("The localpath does not exist '%s'" % localpath)
+ raise Exception("The path does not exist '%s'" % localpath)
+
+
+ # call md5(sum) and shasum
+ try:
+ md5pipe = os.popen('PATH=%s md5sum %s' % (bb.data.getVar('PATH', data, True), localpath))
+ md5data = (md5pipe.readline().split() or [ "" ])[0]
+ md5pipe.close()
+ except OSError:
+ raise Exception("Executing md5sum failed")
+
+ try:
+ shapipe = os.popen('PATH=%s oe_sha256sum %s' % (bb.data.getVar('PATH', data, True), localpath))
+ shadata = (shapipe.readline().split() or [ "" ])[0]
+ shapipe.close()
+ except OSError:
+ raise Exception("Executing shasum failed")
+
+ if no_checksum == True: # we do not have conf/checksums.ini entry
+ try:
+ file = open("%s/checksums.ini" % bb.data.getVar("TMPDIR", data, 1), "a")
+ except:
+ return False
+
+ if not file:
+ raise Exception("Creating checksums.ini failed")
+
+ file.write("[%s]\nmd5=%s\nsha256=%s\n\n" % (src_uri, md5data, shadata))
+ file.close()
+ if not bb.data.getVar("OE_STRICT_CHECKSUMS",data, True):
+ bb.note("This package has no entry in checksums.ini, please add one")
+ bb.note("\n[%s]\nmd5=%s\nsha256=%s" % (src_uri, md5data, shadata))
+ return True
+ else:
+ bb.note("Missing checksum")
+ return False
+
+ if not md5 == md5data:
+ bb.note("The MD5Sums did not match. Wanted: '%s' and Got: '%s'" % (md5,md5data))
+ raise Exception("MD5 Sums do not match. Wanted: '%s' Got: '%s'" % (md5, md5data))
+
+ if not sha256 == shadata:
+ bb.note("The SHA256 Sums do not match. Wanted: '%s' Got: '%s'" % (sha256,shadata))
+ raise Exception("SHA256 Sums do not match. Wanted: '%s' Got: '%s'" % (sha256, shadata))
+
+ return True
+
def base_dep_prepend(d):
- import bb;
#
# Ideally this will check a flag so we will operate properly in
# the case where host == build == target, for now we don't work in
# that case though.
#
- deps = ""
+ deps = "shasum-native coreutils-native"
+ if bb.data.getVar('PN', d, True) == "shasum-native" or bb.data.getVar('PN', d, True) == "stagemanager-native":
+ deps = ""
+ if bb.data.getVar('PN', d, True) == "coreutils-native":
+ deps = "shasum-native"
# INHIBIT_DEFAULT_DEPS doesn't apply to the patch command. Whether or not
# we need that built is the responsibility of the patch function / class, not
# the application.
- patchdeps = bb.data.getVar("PATCHTOOL", d, 1)
- if patchdeps:
- patchdeps = "%s-native" % patchdeps
- if not patchdeps in bb.data.getVar("PROVIDES", d, 1):
- deps = patchdeps
-
if not bb.data.getVar('INHIBIT_DEFAULT_DEPS', d):
if (bb.data.getVar('HOST_SYS', d, 1) !=
bb.data.getVar('BUILD_SYS', d, 1)):
@@ -25,7 +192,6 @@ def base_dep_prepend(d):
return deps
def base_read_file(filename):
- import bb
try:
f = file( filename, "r" )
except IOError, reason:
@@ -34,41 +200,70 @@ def base_read_file(filename):
return f.read().strip()
return None
+def base_ifelse(condition, iftrue = True, iffalse = False):
+ if condition:
+ return iftrue
+ else:
+ return iffalse
+
def base_conditional(variable, checkvalue, truevalue, falsevalue, d):
- import bb
if bb.data.getVar(variable,d,1) == checkvalue:
return truevalue
else:
return falsevalue
-def base_contains(variable, checkvalue, truevalue, falsevalue, d):
- import bb
- if bb.data.getVar(variable,d,1).find(checkvalue) != -1:
- return truevalue
- else:
- return falsevalue
+def base_less_or_equal(variable, checkvalue, truevalue, falsevalue, d):
+ if float(bb.data.getVar(variable,d,1)) <= float(checkvalue):
+ return truevalue
+ else:
+ return falsevalue
+
+def base_version_less_or_equal(variable, checkvalue, truevalue, falsevalue, d):
+ result = bb.vercmp(bb.data.getVar(variable,d,True), checkvalue)
+ if result <= 0:
+ return truevalue
+ else:
+ return falsevalue
+
+def base_contains(variable, checkvalues, truevalue, falsevalue, d):
+ matches = 0
+ if type(checkvalues).__name__ == "str":
+ checkvalues = [checkvalues]
+ for value in checkvalues:
+ if bb.data.getVar(variable,d,1).find(value) != -1:
+ matches = matches + 1
+ if matches == len(checkvalues):
+ return truevalue
+ return falsevalue
def base_both_contain(variable1, variable2, checkvalue, d):
- import bb
if bb.data.getVar(variable1,d,1).find(checkvalue) != -1 and bb.data.getVar(variable2,d,1).find(checkvalue) != -1:
return checkvalue
else:
return ""
DEPENDS_prepend="${@base_dep_prepend(d)} "
+DEPENDS_virtclass-native_prepend="${@base_dep_prepend(d)} "
+DEPENDS_virtclass-nativesdk_prepend="${@base_dep_prepend(d)} "
+
+def base_prune_suffix(var, suffixes, d):
+ # See if var ends with any of the suffixes listed and
+ # remove it if found
+ for suffix in suffixes:
+ if var.endswith(suffix):
+ return var.replace(suffix, "")
+ return var
def base_set_filespath(path, d):
- import os, bb
+ bb.note("base_set_filespath usage is deprecated, %s should be fixed" % d.getVar("P", 1))
filespath = []
+ # The ":" ensures we have an 'empty' override
+ overrides = (bb.data.getVar("OVERRIDES", d, 1) or "") + ":"
for p in path:
- overrides = bb.data.getVar("OVERRIDES", d, 1) or ""
- overrides = overrides + ":"
for o in overrides.split(":"):
filespath.append(os.path.join(p, o))
return ":".join(filespath)
-FILESPATH = "${@base_set_filespath([ "${FILE_DIRNAME}/${PF}", "${FILE_DIRNAME}/${P}", "${FILE_DIRNAME}/${PN}", "${FILE_DIRNAME}/files", "${FILE_DIRNAME}" ], d)}"
-
def oe_filter(f, str, d):
from re import match
return " ".join(filter(lambda x: match(f, x, 0), str.split()))
@@ -187,7 +382,16 @@ oe_libinstall() {
if [ -z "$dir" ]; then
dir=`pwd`
fi
+
dotlai=$libname.lai
+
+ # Sanity check that the libname.lai is unique
+ number_of_files=`(cd $dir; find . -name "$dotlai") | wc -l`
+ if [ $number_of_files -gt 1 ]; then
+ oefatal "oe_libinstall: $dotlai is not unique in $dir"
+ fi
+
+
dir=$dir`(cd $dir;find . -name "$dotlai") | sed "s/^\.//;s/\/$dotlai\$//;q"`
olddir=`pwd`
__runcmd cd $dir
@@ -196,8 +400,12 @@ oe_libinstall() {
# If such file doesn't exist, try to cut version suffix
if [ ! -f "$lafile" ]; then
- libname=`echo "$libname" | sed 's/-[0-9.]*$//'`
- lafile=$libname.la
+ libname1=`echo "$libname" | sed 's/-[0-9.]*$//'`
+ lafile1=$libname.la
+ if [ -f "$lafile1" ]; then
+ libname=$libname1
+ lafile=$lafile1
+ fi
fi
if [ -f "$lafile" ]; then
@@ -219,7 +427,10 @@ oe_libinstall() {
# stop libtool using the final directory name for libraries
# in staging:
__runcmd rm -f $destpath/$libname.la
- __runcmd sed -e 's/^installed=yes$/installed=no/' -e '/^dependency_libs=/s,${WORKDIR}[[:alnum:]/\._+-]*/\([[:alnum:]\._+-]*\),${STAGING_LIBDIR}/\1,g' $dotlai >$destpath/$libname.la
+ __runcmd sed -e 's/^installed=yes$/installed=no/' \
+ -e '/^dependency_libs=/s,${WORKDIR}[[:alnum:]/\._+-]*/\([[:alnum:]\._+-]*\),${STAGING_LIBDIR}/\1,g' \
+ -e "/^dependency_libs=/s,\([[:space:]']\)${libdir},\1${STAGING_LIBDIR},g" \
+ $dotlai >$destpath/$libname.la
else
__runcmd install -m 0644 $dotlai $destpath/$libname.la
fi
@@ -261,6 +472,24 @@ oe_libinstall() {
__runcmd cd "$olddir"
}
+def package_stagefile(file, d):
+
+ if bb.data.getVar('PSTAGING_ACTIVE', d, True) == "1":
+ destfile = file.replace(bb.data.getVar("TMPDIR", d, 1), bb.data.getVar("PSTAGE_TMPDIR_STAGE", d, 1))
+ bb.mkdirhier(os.path.dirname(destfile))
+ #print "%s to %s" % (file, destfile)
+ bb.copyfile(file, destfile)
+
+package_stagefile_shell() {
+ if [ "$PSTAGING_ACTIVE" = "1" ]; then
+ srcfile=$1
+ destfile=`echo $srcfile | sed s#${TMPDIR}#${PSTAGE_TMPDIR_STAGE}#`
+ destdir=`dirname $destfile`
+ mkdir -p $destdir
+ cp -dp $srcfile $destfile
+ fi
+}
+
oe_machinstall() {
# Purpose: Install machine dependent files, if available
# If not available, check if there is a default
@@ -291,18 +520,6 @@ oe_machinstall() {
fi
}
-addtask showdata
-do_showdata[nostamp] = "1"
-python do_showdata() {
- import sys
- # emit variables and shell functions
- bb.data.emit_env(sys.__stdout__, d, True)
- # emit the metadata which isnt valid shell
- for e in d.keys():
- if bb.data.getVarFlag(e, 'python', d):
- sys.__stdout__.write("\npython %s () {\n%s}\n" % (e, bb.data.getVar(e, d, 1)))
-}
-
addtask listtasks
do_listtasks[nostamp] = "1"
python do_listtasks() {
@@ -318,44 +535,95 @@ python do_listtasks() {
addtask clean
do_clean[dirs] = "${TOPDIR}"
do_clean[nostamp] = "1"
-do_clean[bbdepcmd] = ""
python base_do_clean() {
"""clear the build and temp directories"""
dir = bb.data.expand("${WORKDIR}", d)
if dir == '//': raise bb.build.FuncFailed("wrong DATADIR")
- bb.note("removing " + dir)
+ bb.note("removing " + base_path_out(dir, d))
os.system('rm -rf ' + dir)
dir = "%s.*" % bb.data.expand(bb.data.getVar('STAMP', d), d)
- bb.note("removing " + dir)
+ bb.note("removing " + base_path_out(dir, d))
os.system('rm -f '+ dir)
}
-addtask rebuild
+python do_cleanall() {
+ pass
+}
+do_cleanall[recrdeptask] = "do_clean"
+addtask cleanall after do_clean
+
+addtask rebuild after do_${BB_DEFAULT_TASK}
do_rebuild[dirs] = "${TOPDIR}"
do_rebuild[nostamp] = "1"
-do_rebuild[bbdepcmd] = ""
python base_do_rebuild() {
"""rebuild a package"""
- bb.build.exec_task('do_clean', d)
- bb.build.exec_task('do_' + bb.data.getVar('BB_DEFAULT_TASK', d, 1), d)
}
addtask mrproper
do_mrproper[dirs] = "${TOPDIR}"
do_mrproper[nostamp] = "1"
-do_mrproper[bbdepcmd] = ""
python base_do_mrproper() {
"""clear downloaded sources, build and temp directories"""
dir = bb.data.expand("${DL_DIR}", d)
if dir == '/': bb.build.FuncFailed("wrong DATADIR")
bb.debug(2, "removing " + dir)
os.system('rm -rf ' + dir)
- bb.build.exec_task('do_clean', d)
+ bb.build.exec_func('do_clean', d)
+}
+
+addtask distclean
+do_distclean[dirs] = "${TOPDIR}"
+do_distclean[nostamp] = "1"
+python base_do_distclean() {
+ """clear downloaded sources, build and temp directories"""
+
+ bb.build.exec_func('do_clean', d)
+
+ src_uri = bb.data.getVar('SRC_URI', d, 1)
+ if not src_uri:
+ return
+
+ for uri in src_uri.split():
+ if bb.decodeurl(uri)[0] == "file":
+ continue
+
+ try:
+ local = bb.data.expand(bb.fetch.localpath(uri, d), d)
+ except bb.MalformedUrl, e:
+ bb.debug(1, 'Unable to generate local path for malformed uri: %s' % e)
+ else:
+ bb.note("removing %s" % base_path_out(local, d))
+ try:
+ if os.path.exists(local + ".md5"):
+ os.remove(local + ".md5")
+ if os.path.exists(local):
+ os.remove(local)
+ except OSError, e:
+ bb.note("Error in removal: %s" % e)
+}
+
+SCENEFUNCS += "base_scenefunction"
+
+python base_do_setscene () {
+ for f in (bb.data.getVar('SCENEFUNCS', d, 1) or '').split():
+ bb.build.exec_func(f, d)
+ if not os.path.exists(bb.data.getVar('STAMP', d, 1) + ".do_setscene"):
+ bb.build.make_stamp("do_setscene", d)
+}
+do_setscene[selfstamp] = "1"
+addtask setscene before do_fetch
+
+python base_scenefunction () {
+ stamp = bb.data.getVar('STAMP', d, 1) + ".needclean"
+ if os.path.exists(stamp):
+ bb.build.exec_func("do_clean", d)
}
+
addtask fetch
do_fetch[dirs] = "${DL_DIR}"
+do_fetch[depends] = "shasum-native:do_populate_staging"
python base_do_fetch() {
import sys
@@ -371,6 +639,9 @@ python base_do_fetch() {
except bb.fetch.NoMethodError:
(type, value, traceback) = sys.exc_info()
raise bb.build.FuncFailed("No method: %s" % value)
+ except bb.MalformedUrl:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("Malformed URL: %s" % value)
try:
bb.fetch.go(localdata)
@@ -380,6 +651,49 @@ python base_do_fetch() {
except bb.fetch.FetchError:
(type, value, traceback) = sys.exc_info()
raise bb.build.FuncFailed("Fetch failed: %s" % value)
+ except bb.fetch.MD5SumError:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("MD5 failed: %s" % value)
+ except:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("Unknown fetch Error: %s" % value)
+
+
+ # Verify the SHA and MD5 sums we have in OE and check what do
+ # in
+ checksum_paths = bb.data.getVar('BBPATH', d, True).split(":")
+
+ # reverse the list to give precedence to directories that
+ # appear first in BBPATH
+ checksum_paths.reverse()
+
+ checksum_files = ["%s/conf/checksums.ini" % path for path in checksum_paths]
+ try:
+ parser = base_chk_load_parser(checksum_files)
+ except ValueError:
+ bb.note("No conf/checksums.ini found, not checking checksums")
+ return
+ except:
+ bb.note("Creating the CheckSum parser failed: %s:%s" % (sys.exc_info()[0], sys.exc_info()[1]))
+ return
+
+ pv = bb.data.getVar('PV', d, True)
+ pn = bb.data.getVar('PN', d, True)
+
+ # Check each URI
+ for url in src_uri.split():
+ localpath = bb.data.expand(bb.fetch.localpath(url, localdata), localdata)
+ (type,host,path,_,_,params) = bb.decodeurl(url)
+ uri = "%s://%s%s" % (type,host,path)
+ try:
+ if type in [ "http", "https", "ftp", "ftps" ]:
+ if not (base_chk_file_vars(parser, localpath, params, d) or base_chk_file(parser, pn, pv,uri, localpath, d)):
+ if not bb.data.getVar("OE_ALLOW_INSECURE_DOWNLOADS", d, True):
+ bb.fatal("%s-%s: %s has no checksum defined, cannot check archive integrity" % (pn,pv,uri))
+ else:
+ bb.note("%s-%s: %s has no checksum defined, archive integrity not checked" % (pn,pv,uri))
+ except Exception:
+ raise bb.build.FuncFailed("Checksum of '%s' failed" % uri)
}
addtask fetchall after do_fetch
@@ -388,8 +702,59 @@ base_do_fetchall() {
:
}
+addtask checkuri
+do_checkuri[nostamp] = "1"
+python do_checkuri() {
+ import sys
+
+ localdata = bb.data.createCopy(d)
+ bb.data.update_data(localdata)
+
+ src_uri = bb.data.getVar('SRC_URI', localdata, 1)
+
+ try:
+ bb.fetch.init(src_uri.split(),d)
+ except bb.fetch.NoMethodError:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("No method: %s" % value)
+
+ try:
+ bb.fetch.checkstatus(localdata)
+ except bb.fetch.MissingParameterError:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("Missing parameters: %s" % value)
+ except bb.fetch.FetchError:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("Fetch failed: %s" % value)
+ except bb.fetch.MD5SumError:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("MD5 failed: %s" % value)
+ except:
+ (type, value, traceback) = sys.exc_info()
+ raise bb.build.FuncFailed("Unknown fetch Error: %s" % value)
+}
+
+addtask checkuriall after do_checkuri
+do_checkuriall[recrdeptask] = "do_checkuri"
+do_checkuriall[nostamp] = "1"
+base_do_checkuriall() {
+ :
+}
+
+addtask buildall after do_build
+do_buildall[recrdeptask] = "do_build"
+base_do_buildall() {
+ :
+}
+
+def subprocess_setup():
+ import signal
+ # Python installs a SIGPIPE handler by default. This is usually not what
+ # non-Python subprocesses expect.
+ signal.signal(signal.SIGPIPE, signal.SIG_DFL)
+
def oe_unpack_file(file, data, url = None):
- import bb, os
+ import subprocess
if not url:
url = "file://%s" % file
dots = file.split(".")
@@ -402,28 +767,31 @@ def oe_unpack_file(file, data, url = None):
cmd = 'tar x --no-same-owner -f %s' % file
elif file.endswith('.tgz') or file.endswith('.tar.gz') or file.endswith('.tar.Z'):
cmd = 'tar xz --no-same-owner -f %s' % file
- elif file.endswith('.tbz') or file.endswith('.tar.bz2'):
+ elif file.endswith('.tbz') or file.endswith('.tbz2') or file.endswith('.tar.bz2'):
cmd = 'bzip2 -dc %s | tar x --no-same-owner -f -' % file
elif file.endswith('.gz') or file.endswith('.Z') or file.endswith('.z'):
cmd = 'gzip -dc %s > %s' % (file, efile)
elif file.endswith('.bz2'):
cmd = 'bzip2 -dc %s > %s' % (file, efile)
- elif file.endswith('.zip'):
- cmd = 'unzip -q'
+ elif file.endswith('.zip') or file.endswith('.jar'):
+ cmd = 'unzip -q -o'
(type, host, path, user, pswd, parm) = bb.decodeurl(url)
if 'dos' in parm:
cmd = '%s -a' % cmd
cmd = '%s %s' % (cmd, file)
elif os.path.isdir(file):
- filesdir = os.path.realpath(bb.data.getVar("FILESDIR", data, 1))
destdir = "."
- if file[0:len(filesdir)] == filesdir:
- destdir = file[len(filesdir):file.rfind('/')]
- destdir = destdir.strip('/')
- if len(destdir) < 1:
- destdir = "."
- elif not os.access("%s/%s" % (os.getcwd(), destdir), os.F_OK):
- os.makedirs("%s/%s" % (os.getcwd(), destdir))
+ filespath = bb.data.getVar("FILESPATH", data, 1).split(":")
+ for fp in filespath:
+ if file[0:len(fp)] == fp:
+ destdir = file[len(fp):file.rfind('/')]
+ destdir = destdir.strip('/')
+ if len(destdir) < 1:
+ destdir = "."
+ elif not os.access("%s/%s" % (os.getcwd(), destdir), os.F_OK):
+ os.makedirs("%s/%s" % (os.getcwd(), destdir))
+ break
+
cmd = 'cp -pPR %s %s/%s/' % (file, os.getcwd(), destdir)
else:
(type, host, path, user, pswd, parm) = bb.decodeurl(url)
@@ -445,15 +813,26 @@ def oe_unpack_file(file, data, url = None):
if os.path.samefile(file, dest):
return True
+ # Change to subdir before executing command
+ save_cwd = os.getcwd();
+ parm = bb.decodeurl(url)[5]
+ if 'subdir' in parm:
+ newdir = ("%s/%s" % (os.getcwd(), parm['subdir']))
+ bb.mkdirhier(newdir)
+ os.chdir(newdir)
+
cmd = "PATH=\"%s\" %s" % (bb.data.getVar('PATH', data, 1), cmd)
- bb.note("Unpacking %s to %s/" % (file, os.getcwd()))
- ret = os.system(cmd)
+ bb.note("Unpacking %s to %s/" % (base_path_out(file, data), base_path_out(os.getcwd(), data)))
+ ret = subprocess.call(cmd, preexec_fn=subprocess_setup, shell=True)
+
+ os.chdir(save_cwd)
+
return ret == 0
addtask unpack after do_fetch
do_unpack[dirs] = "${WORKDIR}"
python base_do_unpack() {
- import re, os
+ import re
localdata = bb.data.createCopy(d)
bb.data.update_data(localdata)
@@ -466,63 +845,121 @@ python base_do_unpack() {
try:
local = bb.data.expand(bb.fetch.localpath(url, localdata), localdata)
except bb.MalformedUrl, e:
- raise FuncFailed('Unable to generate local path for malformed uri: %s' % e)
- # dont need any parameters for extraction, strip them off
- local = re.sub(';.*$', '', local)
+ raise bb.build.FuncFailed('Unable to generate local path for malformed uri: %s' % e)
+ if not local:
+ raise bb.build.FuncFailed('Unable to locate local file for %s' % url)
local = os.path.realpath(local)
ret = oe_unpack_file(local, localdata, url)
if not ret:
raise bb.build.FuncFailed()
}
+METADATA_SCM = "${@base_get_scm(d)}"
+METADATA_REVISION = "${@base_get_scm_revision(d)}"
+METADATA_BRANCH = "${@base_get_scm_branch(d)}"
+
+def base_get_scm(d):
+ from bb import which
+ baserepo = os.path.dirname(os.path.dirname(which(d.getVar("BBPATH", 1), "classes/base.bbclass")))
+ for (scm, scmpath) in {"svn": ".svn",
+ "git": ".git",
+ "monotone": "_MTN"}.iteritems():
+ if os.path.exists(os.path.join(baserepo, scmpath)):
+ return "%s %s" % (scm, baserepo)
+ return "<unknown> %s" % baserepo
+
+def base_get_scm_revision(d):
+ (scm, path) = d.getVar("METADATA_SCM", 1).split()
+ try:
+ if scm != "<unknown>":
+ return globals()["base_get_metadata_%s_revision" % scm](path, d)
+ else:
+ return scm
+ except KeyError:
+ return "<unknown>"
+
+def base_get_scm_branch(d):
+ (scm, path) = d.getVar("METADATA_SCM", 1).split()
+ try:
+ if scm != "<unknown>":
+ return globals()["base_get_metadata_%s_branch" % scm](path, d)
+ else:
+ return scm
+ except KeyError:
+ return "<unknown>"
+
+def base_get_metadata_monotone_branch(path, d):
+ monotone_branch = "<unknown>"
+ try:
+ monotone_branch = file( "%s/_MTN/options" % path ).read().strip()
+ if monotone_branch.startswith( "database" ):
+ monotone_branch_words = monotone_branch.split()
+ monotone_branch = monotone_branch_words[ monotone_branch_words.index( "branch" )+1][1:-1]
+ except:
+ pass
+ return monotone_branch
+
+def base_get_metadata_monotone_revision(path, d):
+ monotone_revision = "<unknown>"
+ try:
+ monotone_revision = file( "%s/_MTN/revision" % path ).read().strip()
+ if monotone_revision.startswith( "format_version" ):
+ monotone_revision_words = monotone_revision.split()
+ monotone_revision = monotone_revision_words[ monotone_revision_words.index( "old_revision" )+1][1:-1]
+ except IOError:
+ pass
+ return monotone_revision
+
+def base_get_metadata_svn_revision(path, d):
+ revision = "<unknown>"
+ try:
+ revision = file( "%s/.svn/entries" % path ).readlines()[3].strip()
+ except IOError:
+ pass
+ return revision
+
+def base_get_metadata_git_branch(path, d):
+ branch = os.popen('cd %s; PATH=%s git symbolic-ref HEAD 2>/dev/null' % (path, d.getVar("PATH", 1))).read().rstrip()
+
+ if len(branch) != 0:
+ return branch.replace("refs/heads/", "")
+ return "<unknown>"
+
+def base_get_metadata_git_revision(path, d):
+ rev = os.popen("cd %s; PATH=%s git show-ref HEAD 2>/dev/null" % (path, d.getVar("PATH", 1))).read().split(" ")[0].rstrip()
+ if len(rev) != 0:
+ return rev
+ return "<unknown>"
+
addhandler base_eventhandler
python base_eventhandler() {
from bb import note, error, data
from bb.event import Handled, NotHandled, getName
- import os
- messages = {}
- messages["Completed"] = "completed"
- messages["Succeeded"] = "completed"
- messages["Started"] = "started"
- messages["Failed"] = "failed"
name = getName(e)
- msg = ""
- if name.startswith("Pkg"):
- msg += "package %s: " % data.getVar("P", e.data, 1)
- msg += messages.get(name[3:]) or name[3:]
- elif name.startswith("Task"):
- msg += "package %s: task %s: " % (data.getVar("PF", e.data, 1), e.task)
- msg += messages.get(name[4:]) or name[4:]
- elif name.startswith("Build"):
- msg += "build %s: " % e.name
- msg += messages.get(name[5:]) or name[5:]
+ if name == "TaskCompleted":
+ msg = "package %s: task %s is complete." % (data.getVar("PF", e.data, 1), e.task)
elif name == "UnsatisfiedDep":
- msg += "package %s: dependency %s %s" % (e.pkg, e.dep, name[:-3].lower())
- if msg:
- note(msg)
+ msg = "package %s: dependency %s %s" % (e.pkg, e.dep, name[:-3].lower())
+ else:
+ return NotHandled
+
+ # Only need to output when using 1.8 or lower, the UI code handles it
+ # otherwise
+ if (int(bb.__version__.split(".")[0]) <= 1 and int(bb.__version__.split(".")[1]) <= 8):
+ if msg:
+ note(msg)
if name.startswith("BuildStarted"):
bb.data.setVar( 'BB_VERSION', bb.__version__, e.data )
- path_to_bbfiles = bb.data.getVar( 'BBFILES', e.data, 1 )
- path_to_packages = path_to_bbfiles[:path_to_bbfiles.rindex( "packages" )]
- monotone_revision = "<unknown>"
- try:
- monotone_revision = file( "%s/_MTN/revision" % path_to_packages ).read().strip()
- if monotone_revision.startswith( "format_version" ):
- monotone_revision_words = monotone_revision.split()
- monotone_revision = monotone_revision_words[ monotone_revision_words.index( "old_revision" )+1][1:-1]
- except IOError:
- pass
- bb.data.setVar( 'OE_REVISION', monotone_revision, e.data )
- statusvars = ['BB_VERSION', 'OE_REVISION', 'TARGET_ARCH', 'TARGET_OS', 'MACHINE', 'DISTRO', 'DISTRO_VERSION','TARGET_FPU']
- statuslines = ["%-14s = \"%s\"" % (i, bb.data.getVar(i, e.data, 1) or '') for i in statusvars]
- statusmsg = "\nOE Build Configuration:\n%s\n" % '\n'.join(statuslines)
+ statusvars = bb.data.getVar("BUILDCFG_VARS", e.data, 1).split()
+ statuslines = ["%-17s = \"%s\"" % (i, bb.data.getVar(i, e.data, 1) or '') for i in statusvars]
+ statusmsg = "\n%s\n%s\n" % (bb.data.getVar("BUILDCFG_HEADER", e.data, 1), "\n".join(statuslines))
print statusmsg
- needed_vars = [ "TARGET_ARCH", "TARGET_OS" ]
+ needed_vars = bb.data.getVar("BUILDCFG_NEEDEDVARS", e.data, 1).split()
pesteruser = []
for v in needed_vars:
val = bb.data.getVar(v, e.data, 1)
@@ -531,6 +968,18 @@ python base_eventhandler() {
if pesteruser:
bb.fatal('The following variable(s) were not set: %s\nPlease set them directly, or choose a MACHINE or DISTRO that sets them.' % ', '.join(pesteruser))
+ #
+ # Handle removing stamps for 'rebuild' task
+ #
+ if name.startswith("StampUpdate"):
+ for (fn, task) in e.targets:
+ #print "%s %s" % (task, fn)
+ if task == "do_rebuild":
+ dir = "%s.*" % e.stampPrefix[fn]
+ bb.note("Removing stamps: " + dir)
+ os.system('rm -f '+ dir)
+ os.system('touch ' + e.stampPrefix[fn] + '.needclean')
+
if not data in e.__dict__:
return NotHandled
@@ -545,7 +994,6 @@ python base_eventhandler() {
addtask configure after do_unpack do_patch
do_configure[dirs] = "${S} ${B}"
-do_configure[bbdepcmd] = "do_populate_staging"
do_configure[deptask] = "do_populate_staging"
base_do_configure() {
:
@@ -553,7 +1001,6 @@ base_do_configure() {
addtask compile after do_configure
do_compile[dirs] = "${S} ${B}"
-do_compile[bbdepcmd] = "do_populate_staging"
base_do_compile() {
if [ -e Makefile -o -e makefile ]; then
oe_runmake || die "make failed"
@@ -562,25 +1009,156 @@ base_do_compile() {
fi
}
-base_do_stage () {
- :
+
+sysroot_stage_dir() {
+ src="$1"
+ dest="$2"
+ # This will remove empty directories so we can ignore them
+ rmdir "$src" 2> /dev/null || true
+ if [ -d "$src" ]; then
+ mkdir -p "$dest"
+ cp -fpPR "$src"/* "$dest"
+ fi
}
-do_populate_staging[dirs] = "${STAGING_DIR}/${TARGET_SYS}/bin ${STAGING_DIR}/${TARGET_SYS}/lib \
- ${STAGING_DIR}/${TARGET_SYS}/include \
- ${STAGING_DIR}/${BUILD_SYS}/bin ${STAGING_DIR}/${BUILD_SYS}/lib \
- ${STAGING_DIR}/${BUILD_SYS}/include \
+sysroot_stage_libdir() {
+ src="$1"
+ dest="$2"
+
+ olddir=`pwd`
+ cd $src
+ las=$(find . -name \*.la -type f)
+ cd $olddir
+ echo "Found la files: $las"
+ for i in $las
+ do
+ sed -e 's/^installed=yes$/installed=no/' \
+ -e '/^dependency_libs=/s,${WORKDIR}[[:alnum:]/\._+-]*/\([[:alnum:]\._+-]*\),${STAGING_LIBDIR}/\1,g' \
+ -e "/^dependency_libs=/s,\([[:space:]']\)${libdir},\1${STAGING_LIBDIR},g" \
+ -i $src/$i
+ done
+ sysroot_stage_dir $src $dest
+}
+
+sysroot_stage_dirs() {
+ from="$1"
+ to="$2"
+
+ sysroot_stage_dir $from${includedir} $to${STAGING_INCDIR}
+ if [ "${BUILD_SYS}" = "${HOST_SYS}" ]; then
+ sysroot_stage_dir $from${bindir} $to${STAGING_DIR_HOST}${bindir}
+ sysroot_stage_dir $from${sbindir} $to${STAGING_DIR_HOST}${sbindir}
+ sysroot_stage_dir $from${base_bindir} $to${STAGING_DIR_HOST}${base_bindir}
+ sysroot_stage_dir $from${base_sbindir} $to${STAGING_DIR_HOST}${base_sbindir}
+ sysroot_stage_dir $from${libexecdir} $to${STAGING_DIR_HOST}${libexecdir}
+ if [ "${prefix}/lib" != "${libdir}" ]; then
+ # python puts its files in here, make sure they are staged as well
+ autotools_stage_dir $from/${prefix}/lib $to${STAGING_DIR_HOST}${prefix}/lib
+ fi
+ fi
+ if [ -d $from${libdir} ]
+ then
+ sysroot_stage_libdir $from/${libdir} $to${STAGING_LIBDIR}
+ fi
+ if [ -d $from${base_libdir} ]
+ then
+ sysroot_stage_libdir $from${base_libdir} $to${STAGING_DIR_HOST}${base_libdir}
+ fi
+ sysroot_stage_dir $from${datadir} $to${STAGING_DATADIR}
+}
+
+sysroot_stage_all() {
+ sysroot_stage_dirs ${D} ${SYSROOT_DESTDIR}
+}
+
+def is_legacy_staging(d):
+ stagefunc = bb.data.getVar('do_stage', d, True)
+ legacy = True
+ if stagefunc is None:
+ legacy = False
+ elif stagefunc.strip() == "autotools_stage_all":
+ legacy = False
+ elif stagefunc.strip() == "do_stage_native" and bb.data.getVar('AUTOTOOLS_NATIVE_STAGE_INSTALL', d, 1) == "1":
+ legacy = False
+ elif bb.data.getVar('NATIVE_INSTALL_WORKS', d, 1) == "1":
+ legacy = False
+ if bb.data.getVar('PSTAGE_BROKEN_DESTDIR', d, 1) == "1":
+ legacy = True
+ if bb.data.getVar('FORCE_LEGACY_STAGING', d, 1) == "1":
+ legacy = True
+ return legacy
+
+do_populate_staging[dirs] = "${STAGING_DIR_TARGET}/${bindir} ${STAGING_DIR_TARGET}/${libdir} \
+ ${STAGING_DIR_TARGET}/${includedir} \
+ ${STAGING_BINDIR_NATIVE} ${STAGING_LIBDIR_NATIVE} \
+ ${STAGING_INCDIR_NATIVE} \
${STAGING_DATADIR} \
${S} ${B}"
-addtask populate_staging after do_package_write
+# Could be compile but populate_staging and do_install shouldn't run at the same time
+addtask populate_staging after do_install
+
+SYSROOT_PREPROCESS_FUNCS ?= ""
+SYSROOT_DESTDIR = "${WORKDIR}/sysroot-destdir/"
+SYSROOT_LOCK = "${STAGING_DIR}/staging.lock"
+
+python populate_staging_prehook () {
+ return
+}
+
+python populate_staging_posthook () {
+ return
+}
+
+packagedstaging_fastpath () {
+ :
+}
python do_populate_staging () {
- bb.build.exec_func('do_stage', d)
+ #
+ # if do_stage exists, we're legacy. In that case run the do_stage,
+ # modify the SYSROOT_DESTDIR variable and then run the staging preprocess
+ # functions against staging directly.
+ #
+ # Otherwise setup a destdir, copy the results from do_install
+ # and run the staging preprocess against that
+ #
+ pstageactive = (bb.data.getVar("PSTAGING_ACTIVE", d, True) == "1")
+ lockfile = bb.data.getVar("SYSROOT_LOCK", d, True)
+ stagefunc = bb.data.getVar('do_stage', d, True)
+ legacy = is_legacy_staging(d)
+ if legacy:
+ bb.data.setVar("SYSROOT_DESTDIR", "", d)
+ bb.note("Legacy staging mode for %s" % bb.data.getVar("FILE", d, True))
+ if bb.data.getVarFlags('do_stage', d) is None:
+ bb.fatal("This recipe (%s) has a do_stage_prepend or do_stage_append and do_stage now doesn't exist. Please rename this to do_stage()" % bb.data.getVar("FILE", d, True))
+ lock = bb.utils.lockfile(lockfile)
+ bb.build.exec_func('populate_staging_prehook', d)
+ bb.build.exec_func('do_stage', d)
+ for f in (bb.data.getVar('SYSROOT_PREPROCESS_FUNCS', d, True) or '').split():
+ bb.build.exec_func(f, d)
+ bb.build.exec_func('populate_staging_posthook', d)
+ bb.utils.unlockfile(lock)
+ else:
+ dest = bb.data.getVar('D', d, True)
+ sysrootdest = bb.data.expand('${SYSROOT_DESTDIR}${STAGING_DIR_TARGET}', d)
+ bb.mkdirhier(sysrootdest)
+
+ bb.build.exec_func("sysroot_stage_all", d)
+ #os.system('cp -pPR %s/* %s/' % (dest, sysrootdest))
+ for f in (bb.data.getVar('SYSROOT_PREPROCESS_FUNCS', d, True) or '').split():
+ bb.build.exec_func(f, d)
+ bb.build.exec_func("packagedstaging_fastpath", d)
+
+ lock = bb.utils.lockfile(lockfile)
+ os.system(bb.data.expand('cp -pPR ${SYSROOT_DESTDIR}${TMPDIR}/* ${TMPDIR}/', d))
+ bb.utils.unlockfile(lock)
}
addtask install after do_compile
do_install[dirs] = "${D} ${S} ${B}"
+# Remove and re-create ${D} so that is it guaranteed to be empty
+do_install[cleandirs] = "${D}"
base_do_install() {
:
@@ -594,6 +1172,8 @@ addtask build after do_populate_staging
do_build = ""
do_build[func] = "1"
+inherit packagedata
+
# Functions that update metadata based on files outputted
# during the build process.
@@ -614,69 +1194,23 @@ def explode_deps(s):
r.append(i)
return r
-def packaged(pkg, d):
- import os, bb
- return os.access(bb.data.expand('${STAGING_DIR}/pkgdata/runtime/%s.packaged' % pkg, d), os.R_OK)
-
-def read_pkgdatafile(fn):
- pkgdata = {}
-
- def decode(str):
- import codecs
- c = codecs.getdecoder("string_escape")
- return c(str)[0]
-
- import os
- if os.access(fn, os.R_OK):
- import re
- f = file(fn, 'r')
- lines = f.readlines()
- f.close()
- r = re.compile("([^:]+):\s*(.*)")
- for l in lines: