summaryrefslogtreecommitdiff
path: root/scripts
diff options
context:
space:
mode:
authorAlexey Neyman <stilor@att.net>2017-03-13 02:41:09 (GMT)
committerAlexey Neyman <stilor@att.net>2017-03-13 02:41:09 (GMT)
commitb090e0f74d1ca0c0c45ec416c139f709a8e28f61 (patch)
treeec16c388b5505a4d369f1614c394e5c339e23942 /scripts
parent8600f3ce56f67a2a0d7b4a14eb9e8b1f0ec49dec (diff)
Fix up ld.so symlinks for musl
Convert absolute targets to relative so that they are valid on the host, too. The procedure is very similar to uclibc, so it is moved into a common function. Signed-off-by: Alexey Neyman <stilor@att.net>
Diffstat (limited to 'scripts')
-rw-r--r--scripts/build/libc/musl.sh4
-rw-r--r--scripts/build/libc/uClibc.sh48
-rw-r--r--scripts/functions87
3 files changed, 91 insertions, 48 deletions
diff --git a/scripts/build/libc/musl.sh b/scripts/build/libc/musl.sh
index 3d6fe04..5a53fd0 100644
--- a/scripts/build/libc/musl.sh
+++ b/scripts/build/libc/musl.sh
@@ -29,7 +29,9 @@ do_libc() {
}
do_libc_post_cc() {
- :
+ # MUSL creates dynamic linker symlink with absolute path - which works on the
+ # target but not on the host. We want our cross-ldd tool to work.
+ CT_MultilibFixupLDSO
}
do_libc_backend() {
diff --git a/scripts/build/libc/uClibc.sh b/scripts/build/libc/uClibc.sh
index fcabee8..9f1eb37 100644
--- a/scripts/build/libc/uClibc.sh
+++ b/scripts/build/libc/uClibc.sh
@@ -453,51 +453,5 @@ do_libc_post_cc() {
# file in /lib. Thus, need to do this after all the variants are built.
# Moreover, need to do this after the final compiler is built: on targets
# that use elf2flt, the core compilers cannot find ld when running elf2flt.
- CT_DoStep INFO "Checking dynamic linker symlinks"
- CT_mkdir_pushd "${CT_BUILD_DIR}/build-libc-post_cc"
- echo "int main(void) { return 0; }" > test-ldso.c
- CT_IterateMultilibs do_libc_ldso_fixup ldso_fixup
- CT_Popd
- CT_EndStep
-}
-
-do_libc_ldso_fixup() {
- local multi_dir multi_os_dir multi_root multi_flags multi_index multi_count
- local binary
- local ldso ldso_f ldso_d multilib_dir
-
- for arg in "$@"; do
- eval "${arg// /\\ }"
- done
-
- CT_DoLog EXTRA "Checking dynamic linker for multilib '${multi_flags}'"
-
- multilib_dir="/lib/${multi_os_dir}"
- CT_SanitizeVarDir multilib_dir
-
- CT_DoExecLog ALL "${CT_TARGET}-${CT_CC}" -o test-ldso ../test-ldso.c ${multi_flags}
- if [ -r "test-ldso.gdb" ]; then
- binary="test-ldso.gdb"
- else
- binary="test-ldso"
- fi
- if ${CT_TARGET}-readelf -Wl "${binary}" | grep -q 'Requesting program interpreter: '; then
- ldso=$( ${CT_TARGET}-readelf -Wl "${binary}" | \
- grep 'Requesting program interpreter: ' | \
- sed -e 's,.*: ,,' -e 's,\].*,,' )
- fi
- CT_DoLog DEBUG "Detected dynamic linker for multilib '${multi_flags}': '${ldso}'"
-
- ldso_d="${ldso%/ld*.so.*}"
- ldso_f="${ldso##*/}"
- # Create symlink if GCC produced an executable, dynamically linked, it was requesting
- # a linker not in the current directory, and there is no such file in the expected
- # ldso dir.
- if [ -n "${ldso}" -a "${ldso_d}" != "${multilib_dir}" -a ! -r "${multi_root}${ldso}" ]; then
- # Convert ldso_d to "how many levels we need to go up" and remove
- # leading slash.
- ldso_d=$( echo "${ldso_d#/}" | sed 's,[^/]\+,..,g' )
- CT_DoExecLog ALL ln -sf "${ldso_d}${multilib_dir}/${ldso_f}" \
- "${multi_root}${ldso}"
- fi
+ CT_MultilibFixupLDSO
}
diff --git a/scripts/functions b/scripts/functions
index 8b12d8e..3ef7bf6 100644
--- a/scripts/functions
+++ b/scripts/functions
@@ -1815,3 +1815,90 @@ CT_SymlinkToolsMultilib()
;;
esac
}
+
+# Helper (iterator) for CT_MultilibFixupLDSO
+CT__FixupLDSO()
+{
+ local multi_dir multi_os_dir multi_root multi_flags multi_index multi_count
+ local binary
+ local ldso ldso_l ldso_f ldso_d ldso_u multilib_dir
+
+ for arg in "$@"; do
+ eval "${arg// /\\ }"
+ done
+
+ CT_DoLog EXTRA "Checking dynamic linker for multilib '${multi_flags}'"
+
+ multilib_dir="/lib/${multi_os_dir}"
+ CT_SanitizeVarDir multilib_dir
+
+ CT_DoExecLog ALL "${CT_TARGET}-${CT_CC}" -o test-ldso ../test-ldso.c ${multi_flags}
+ if [ -r "test-ldso.gdb" ]; then
+ binary="test-ldso.gdb"
+ else
+ binary="test-ldso"
+ fi
+ if ${CT_TARGET}-readelf -Wl "${binary}" | grep -q 'Requesting program interpreter: '; then
+ ldso=$( ${CT_TARGET}-readelf -Wl "${binary}" | \
+ grep 'Requesting program interpreter: ' | \
+ sed -e 's,.*: ,,' -e 's,\].*,,' )
+ fi
+ CT_DoLog DEBUG "Detected dynamic linker for multilib '${multi_flags}': '${ldso}'"
+
+ # Create symlink if GCC produced a dynamically linked executable.
+ if [ -z "${ldso}" ]; then
+ return # Probably, we're building a static toolchain.
+ fi
+
+ ldso_d="${ldso%/ld*.so.*}"
+ ldso_f="${ldso##*/}"
+
+ # Convert ldso_d to "how many levels we need to go up" and remove
+ # leading slash.
+ ldso_u=$( echo "${ldso_d#/}" | sed 's,[^/]\+,..,g' )
+
+ # If the requested dynamic linker exists, but is a symlink - check that it is either
+ # relative (in which case, if it is readable, we trust libc to have created it properly)
+ # or otherwise, convert it from absolute (target) path to a relative path that works on
+ # both host & target.
+ if [ -L "${multi_root}${ldso}" ]; then
+ ldso_l=`readlink "${multi_root}${ldso}"`
+ case "${ldso_l}" in
+ /*) # Absolute, convert to relative
+ if [ -r "${multi_root}${ldso_l}" ]; then
+ CT_DoExecLog ALL ln -sfv "${ldso_u}${ldso_l}" "${multi_root}${ldso}"
+ else
+ CT_DoLog WARN "Compiler selects '${ldso}' as dynamic linker for '${multi_flags}'"
+ CT_DoLog WARN "but '${ldso}' is a symlink to '${ldso_l}' which is not valid on target."
+ fi
+ ;;
+ *) # Relative, must be readable
+ if [ ! -r "${multi_root}${ldso}" ]; then
+ CT_DoLog WARN "Compiler selects '${ldso}' as dynamic linker for '${multi_flags}'"
+ CT_DoLog WARN "but '${ldso}' is a symlink to '${ldso_l}' which is invalid relative symlink."
+ fi
+ ;;
+ esac
+ return
+ elif [ -r "${multi_root}${ldso}" ]; then
+ return # Not a symlink but readable - looks like libc installed a real executable.
+ fi
+
+ # Is it requesting a linker not in the current directory? uClibc case.
+ if [ "${ldso_d}" != "${multilib_dir}" ]; then
+ CT_DoExecLog ALL ln -sfv "${ldso_u}${multilib_dir}/${ldso_f}" \
+ "${multi_root}${ldso}"
+ fi
+}
+
+# Go over multilib variants and check that the requested dynamic linker
+# is present and resolves on both target and host.
+CT_MultilibFixupLDSO()
+{
+ CT_DoStep INFO "Checking dynamic linker symlinks"
+ CT_mkdir_pushd "${CT_BUILD_DIR}/build-libc-check-ldso"
+ echo "int main(void) { return 0; }" > test-ldso.c
+ CT_IterateMultilibs CT__FixupLDSO ldso_fixup
+ CT_Popd
+ CT_EndStep
+}