diff options
author | Joshua Lock <josh@linux.intel.com> | 2010-02-16 17:40:23 +0000 |
---|---|---|
committer | Joshua Lock <josh@linux.intel.com> | 2010-02-18 10:38:29 +0000 |
commit | ef246b44b95c40f68c9d9c7a93ed995a33824573 (patch) | |
tree | 6f54f1f6bd00a9b115c784ac76e327592e715f11 /meta | |
parent | b694d3c3f9764eb0659c60e533d39bd5f3ab8259 (diff) | |
download | poky-ef246b44b95c40f68c9d9c7a93ed995a33824573.tar.gz |
relocatable.bbclass: Enhancements to rpath replacement algorithm
This patch removes the hard coded number of parent directory operators ( /..)
placed into the rpath and instead fully dynamically generates the rpath entries
based on the current rpath.
Theoretically this patch means we can now make cross packages relocatable but
this is *not* enabled as chrpath can only set a new rpath of the same length
or shorter than the existing rpath. Due to the amount of parent directory
jumps we need to encode in the rpath this can easily fail when TMPDIR is in a
short namespace (e.g. /usr/poky).
Signed-off-by: Joshua Lock <josh@linux.intel.com>
Diffstat (limited to 'meta')
-rw-r--r-- | meta/classes/relocatable.bbclass | 53 |
1 files changed, 38 insertions, 15 deletions
diff --git a/meta/classes/relocatable.bbclass b/meta/classes/relocatable.bbclass index 7155503c9f..37e6610131 100644 --- a/meta/classes/relocatable.bbclass +++ b/meta/classes/relocatable.bbclass | |||
@@ -1,16 +1,24 @@ | |||
1 | SYSROOT_PREPROCESS_FUNCS += "relocatable_binaries_preprocess" | 1 | SYSROOT_PREPROCESS_FUNCS += "relocatable_binaries_preprocess" |
2 | 2 | ||
3 | CHRPATH_BIN ?= "chrpath" | 3 | CHRPATH_BIN ?= "chrpath" |
4 | PREPROCESS_RELOCATE_DIRS ?= "" | ||
4 | 5 | ||
5 | def rpath_replace (path, d): | 6 | def rpath_replace (path, d): |
6 | import subprocess as sub | 7 | import subprocess as sub |
7 | 8 | ||
8 | cmd = bb.data.expand('${CHRPATH_BIN}', d) | 9 | cmd = bb.data.expand('${CHRPATH_BIN}', d) |
9 | 10 | ||
10 | for root, dirs, files in os.walk(path): | 11 | bindirs = bb.data.expand("${bindir} ${sbindir} ${base_sbindir} ${base_bindir} ${PREPROCESS_RELOCATE_DIRS}", d).split() |
11 | for file in files: | 12 | tmpdir = bb.data.getVar('TMPDIR', d) |
12 | fpath = root + '/' + file | 13 | basedir = bb.data.expand('${base_prefix}', d) |
13 | if '/bin/' in fpath: | 14 | |
15 | for d in bindirs: | ||
16 | dir = path + "/" + d | ||
17 | bb.note("Checking %s for binaries to process" % dir) | ||
18 | if os.path.exists(dir): | ||
19 | for file in os.listdir(dir): | ||
20 | fpath = dir + "/" + file | ||
21 | #bb.note("Testing %s for relocatability" % fpath) | ||
14 | p = sub.Popen([cmd, '-l', fpath],stdout=sub.PIPE,stderr=sub.PIPE) | 22 | p = sub.Popen([cmd, '-l', fpath],stdout=sub.PIPE,stderr=sub.PIPE) |
15 | err, out = p.communicate() | 23 | err, out = p.communicate() |
16 | # If returned succesfully, process stderr for results | 24 | # If returned succesfully, process stderr for results |
@@ -21,19 +29,34 @@ def rpath_replace (path, d): | |||
21 | rpaths = curr_rpath.split(":") | 29 | rpaths = curr_rpath.split(":") |
22 | new_rpaths = [] | 30 | new_rpaths = [] |
23 | for rpath in rpaths: | 31 | for rpath in rpaths: |
24 | depth = fpath.partition(path)[2].count('/') | 32 | # If rpath is already dynamic continue |
25 | if depth == 3: | 33 | if rpath.find("$ORIGIN") != -1: |
26 | # / is two levels up | 34 | continue |
27 | root = "$ORIGIN/../.." | 35 | # If the rpath shares a root with base_prefix determine a new dynamic rpath from the |
36 | # base_prefix shared root | ||
37 | if rpath.find(basedir) != -1: | ||
38 | depth = fpath.partition(basedir)[2].count('/') | ||
39 | libpath = rpath.partition(basedir)[2].strip() | ||
40 | # otherwise (i.e. cross packages) determine a shared root based on the TMPDIR | ||
41 | # NOTE: This will not work reliably for cross packages, particularly in the case | ||
42 | # where your TMPDIR is a short path (i.e. /usr/poky) as chrpath cannot insert an | ||
43 | # rpath longer than that which is already set. | ||
28 | else: | 44 | else: |
29 | root = "$ORIGIN/.." | 45 | depth = fpath.rpartition(tmpdir)[2].count('/') |
46 | libpath = rpath.partition(tmpdir)[2].strip() | ||
47 | |||
48 | base = "$ORIGIN" | ||
49 | while depth > 1: | ||
50 | base += "/.." | ||
51 | depth-=1 | ||
52 | new_rpaths.append("%s%s" % (base, libpath)) | ||
30 | 53 | ||
31 | # kill everything up to "/" | 54 | # if we have modified some rpaths call chrpath to update the binary |
32 | new_rpaths.append("%s%s" % (root, rpath.partition(path)[2].strip())) | 55 | if len(new_rpaths): |
33 | args = ":".join(new_rpaths) | 56 | args = ":".join(new_rpaths) |
34 | #bb.note("Setting rpath to " + args) | 57 | #bb.note("Setting rpath to " + args) |
35 | sub.call([cmd, '-r', args, fpath]) | 58 | sub.call([cmd, '-r', args, fpath]) |
36 | 59 | ||
37 | python relocatable_binaries_preprocess() { | 60 | python relocatable_binaries_preprocess() { |
38 | rpath_replace(bb.data.getVar('base_prefix', d, True), d) | 61 | rpath_replace(bb.data.expand('${SYSROOT_DESTDIR}', d), d) |
39 | } | 62 | } |