1 |
commit: 31c9c68d7e96070166fe385141400fa3bcb5950e |
2 |
Author: Zac Medico <zmedico <AT> gentoo <DOT> org> |
3 |
AuthorDate: Wed Jun 29 09:18:21 2011 +0000 |
4 |
Commit: Zac Medico <zmedico <AT> gentoo <DOT> org> |
5 |
CommitDate: Wed Jun 29 09:18:21 2011 +0000 |
6 |
URL: http://git.overlays.gentoo.org/gitweb/?p=proj/portage.git;a=commit;h=31c9c68d |
7 |
|
8 |
Detect/create missing soname symlinks for libs. |
9 |
|
10 |
This will allow us to safely use the ldconfig -X option for all |
11 |
ldconfig calls, an thereby avoid having ldconfig override our own |
12 |
soname symlink policy which allows preserve-libs to work correctly |
13 |
when libraries are downgraded as discussed in bug 373341. |
14 |
|
15 |
--- |
16 |
pym/_emerge/EbuildPhase.py | 10 ++++ |
17 |
pym/portage/package/ebuild/doebuild.py | 81 +++++++++++++++++++++++++++++++- |
18 |
2 files changed, 90 insertions(+), 1 deletions(-) |
19 |
|
20 |
diff --git a/pym/_emerge/EbuildPhase.py b/pym/_emerge/EbuildPhase.py |
21 |
index 306932f..954c033 100644 |
22 |
--- a/pym/_emerge/EbuildPhase.py |
23 |
+++ b/pym/_emerge/EbuildPhase.py |
24 |
@@ -18,6 +18,7 @@ portage.proxy.lazyimport.lazyimport(globals(), |
25 |
'portage.package.ebuild.doebuild:_check_build_log,' + \ |
26 |
'_post_phase_cmds,_post_phase_userpriv_perms,' + \ |
27 |
'_post_src_install_chost_fix,' + \ |
28 |
+ '_post_src_install_soname_symlinks,' + \ |
29 |
'_post_src_install_uid_fix,_postinst_bsdflags,' + \ |
30 |
'_preinst_bsdflags' |
31 |
) |
32 |
@@ -254,6 +255,15 @@ class EbuildPhase(CompositeTask): |
33 |
noiselevel=-1) |
34 |
self._die_hooks() |
35 |
return |
36 |
+ |
37 |
+ if self.phase == "install": |
38 |
+ out = portage.StringIO() |
39 |
+ _post_src_install_soname_symlinks(self.settings, out) |
40 |
+ msg = _unicode_decode(out.getvalue(), |
41 |
+ encoding=_encodings['content'], errors='replace') |
42 |
+ if msg: |
43 |
+ self.scheduler.output(msg, log_path=log_path) |
44 |
+ |
45 |
self._current_task = None |
46 |
self.wait() |
47 |
return |
48 |
|
49 |
diff --git a/pym/portage/package/ebuild/doebuild.py b/pym/portage/package/ebuild/doebuild.py |
50 |
index 9df7dc7..35a0b0f 100644 |
51 |
--- a/pym/portage/package/ebuild/doebuild.py |
52 |
+++ b/pym/portage/package/ebuild/doebuild.py |
53 |
@@ -5,6 +5,7 @@ __all__ = ['doebuild', 'doebuild_environment', 'spawn', 'spawnebuild'] |
54 |
|
55 |
import codecs |
56 |
import gzip |
57 |
+import errno |
58 |
from itertools import chain |
59 |
import logging |
60 |
import os as _os |
61 |
@@ -1612,12 +1613,90 @@ def _post_src_install_uid_fix(mysettings, out): |
62 |
mode='w', encoding=_encodings['repo.content'], |
63 |
errors='strict').write(v + '\n') |
64 |
|
65 |
+ _reapply_bsdflags_to_image(mysettings) |
66 |
+ |
67 |
+def _reapply_bsdflags_to_image(mysettings): |
68 |
+ """ |
69 |
+ Reapply flags saved and removed by _preinst_bsdflags. |
70 |
+ """ |
71 |
if bsd_chflags: |
72 |
- # Restore all of the flags saved above. |
73 |
os.system("mtree -e -p %s -U -k flags < %s > /dev/null" % \ |
74 |
(_shell_quote(mysettings["D"]), |
75 |
_shell_quote(os.path.join(mysettings["T"], "bsdflags.mtree")))) |
76 |
|
77 |
+def _post_src_install_soname_symlinks(mysettings, out): |
78 |
+ """ |
79 |
+ Check that libraries in $D have corresponding soname symlinks. |
80 |
+ If symlinks are missing then create them and trigger a QA Notice. |
81 |
+ This requires $PORTAGE_BUILDDIR/build-info/NEEDED.ELF.2 for |
82 |
+ operation. |
83 |
+ """ |
84 |
+ |
85 |
+ image_dir = mysettings["D"] |
86 |
+ needed_filename = os.path.join(mysettings["PORTAGE_BUILDDIR"], |
87 |
+ "build-info", "NEEDED.ELF.2") |
88 |
+ |
89 |
+ try: |
90 |
+ lines = codecs.open(_unicode_encode(needed_filename, |
91 |
+ encoding=_encodings['fs'], errors='strict'), |
92 |
+ 'r', encoding=_encodings['repo.content'], |
93 |
+ errors='replace').readlines() |
94 |
+ except IOError as e: |
95 |
+ if e.errno not in (errno.ENOENT, errno.ESTALE): |
96 |
+ raise |
97 |
+ return |
98 |
+ |
99 |
+ missing_symlinks = [] |
100 |
+ |
101 |
+ # Parse NEEDED.ELF.2 like LinkageMapELF.rebuild() does. |
102 |
+ for l in lines: |
103 |
+ l = l.rstrip("\n") |
104 |
+ if not l: |
105 |
+ continue |
106 |
+ fields = l.split(";") |
107 |
+ if len(fields) < 5: |
108 |
+ portage.util.writemsg_level(_("\nWrong number of fields " \ |
109 |
+ "in %s: %s\n\n") % (needed_filename, l), |
110 |
+ level=logging.ERROR, noiselevel=-1) |
111 |
+ continue |
112 |
+ |
113 |
+ obj, soname = fields[1:3] |
114 |
+ if not soname: |
115 |
+ continue |
116 |
+ |
117 |
+ obj_file_path = os.path.join(image_dir, obj.lstrip(os.sep)) |
118 |
+ sym_file_path = os.path.join(os.path.dirname(obj_file_path), soname) |
119 |
+ try: |
120 |
+ os.lstat(sym_file_path) |
121 |
+ except OSError as e: |
122 |
+ if e.errno not in (errno.ENOENT, errno.ESTALE): |
123 |
+ raise |
124 |
+ else: |
125 |
+ continue |
126 |
+ |
127 |
+ missing_symlinks.append((obj, soname)) |
128 |
+ |
129 |
+ if not missing_symlinks: |
130 |
+ return |
131 |
+ |
132 |
+ qa_msg = ["QA Notice: Missing soname symlink(s) " + \ |
133 |
+ "will be automatically created:"] |
134 |
+ qa_msg.append("") |
135 |
+ qa_msg.extend("\t%s -> %s" % (os.path.join( |
136 |
+ os.path.dirname(obj).lstrip(os.sep), soname), |
137 |
+ os.path.basename(obj)) |
138 |
+ for obj, soname in missing_symlinks) |
139 |
+ qa_msg.append("") |
140 |
+ for line in qa_msg: |
141 |
+ eqawarn(line, key=mysettings.mycpv, out=out) |
142 |
+ |
143 |
+ _preinst_bsdflags(mysettings) |
144 |
+ for obj, soname in missing_symlinks: |
145 |
+ obj_file_path = os.path.join(image_dir, obj.lstrip(os.sep)) |
146 |
+ sym_file_path = os.path.join(os.path.dirname(obj_file_path), soname) |
147 |
+ os.symlink(os.path.basename(obj_file_path), sym_file_path) |
148 |
+ _reapply_bsdflags_to_image(mysettings) |
149 |
+ |
150 |
def _merge_unicode_error(errors): |
151 |
lines = [] |