aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZac Medico <zmedico@gentoo.org>2018-03-26 20:19:10 -0700
committerZac Medico <zmedico@gentoo.org>2018-03-27 21:38:53 -0700
commita67dc215adb52392505d03870c236e828dca3625 (patch)
treee87f4efa2d358ad504a22c67873c379c16b4d1cd
parentemerge --autounmask: prevent unmask due to unsatisfied REQUIRED_USE (bug 622462) (diff)
downloadportage-a67dc215adb52392505d03870c236e828dca3625.tar.gz
portage-a67dc215adb52392505d03870c236e828dca3625.tar.bz2
portage-a67dc215adb52392505d03870c236e828dca3625.zip
prepstrip: rename to bin/estrip (refactor for EAPI 7 dostrip)
This matches the rename in portage-mgorny.
-rwxr-xr-xbin/ebuild-helpers/prepstrip400
-rwxr-xr-xbin/estrip403
2 files changed, 405 insertions, 398 deletions
diff --git a/bin/ebuild-helpers/prepstrip b/bin/ebuild-helpers/prepstrip
index 2136e0d4d..0ec4c16b3 100755
--- a/bin/ebuild-helpers/prepstrip
+++ b/bin/ebuild-helpers/prepstrip
@@ -2,402 +2,6 @@
# Copyright 1999-2018 Gentoo Foundation
# Distributed under the terms of the GNU General Public License v2
-source "${PORTAGE_BIN_PATH}"/helper-functions.sh || exit 1
+source "${PORTAGE_BIN_PATH}"/isolated-functions.sh || exit 1
-# avoid multiple calls to `has`. this creates things like:
-# FEATURES_foo=false
-# if "foo" is not in $FEATURES
-tf() { "$@" && echo true || echo false ; }
-exp_tf() {
- local flag var=$1
- shift
- for flag in "$@" ; do
- eval ${var}_${flag}=$(tf has ${flag} ${!var})
- done
-}
-exp_tf FEATURES compressdebug installsources nostrip splitdebug xattr
-exp_tf RESTRICT binchecks installsources splitdebug strip
-
-if ! ___eapi_has_prefix_variables; then
- EPREFIX= ED=${D}
-fi
-
-banner=false
-SKIP_STRIP=false
-if ${RESTRICT_strip} || ${FEATURES_nostrip} ; then
- SKIP_STRIP=true
- banner=true
- ${FEATURES_installsources} || exit 0
-fi
-
-PRESERVE_XATTR=false
-if [[ ${KERNEL} == linux ]] && ${FEATURES_xattr} ; then
- PRESERVE_XATTR=true
- if type -P getfattr >/dev/null && type -P setfattr >/dev/null ; then
- dump_xattrs() {
- getfattr -d -m - --absolute-names "$1"
- }
- restore_xattrs() {
- setfattr --restore=-
- }
- else
- dump_xattrs() {
- PYTHONPATH=${PORTAGE_PYTHONPATH:-${PORTAGE_PYM_PATH}} \
- "${PORTAGE_PYTHON:-/usr/bin/python}" \
- "${PORTAGE_BIN_PATH}/xattr-helper.py" --dump < <(echo -n "$1")
- }
- restore_xattrs() {
- PYTHONPATH=${PORTAGE_PYTHONPATH:-${PORTAGE_PYM_PATH}} \
- "${PORTAGE_PYTHON:-/usr/bin/python}" \
- "${PORTAGE_BIN_PATH}/xattr-helper.py" --restore
- }
- fi
-fi
-
-# look up the tools we might be using
-for t in STRIP:strip OBJCOPY:objcopy READELF:readelf ; do
- v=${t%:*} # STRIP
- t=${t#*:} # strip
- eval ${v}=\"${!v:-${CHOST}-${t}}\"
- type -P -- ${!v} >/dev/null || eval ${v}=${t}
-done
-
-# Figure out what tool set we're using to strip stuff
-unset SAFE_STRIP_FLAGS DEF_STRIP_FLAGS SPLIT_STRIP_FLAGS
-case $(${STRIP} --version 2>/dev/null) in
-*elfutils*) # dev-libs/elfutils
- # elfutils default behavior is always safe, so don't need to specify
- # any flags at all
- SAFE_STRIP_FLAGS=""
- DEF_STRIP_FLAGS="--remove-comment"
- SPLIT_STRIP_FLAGS="-f"
- ;;
-*GNU*) # sys-devel/binutils
- # We'll leave out -R .note for now until we can check out the relevance
- # of the section when it has the ALLOC flag set on it ...
- SAFE_STRIP_FLAGS="--strip-unneeded"
- DEF_STRIP_FLAGS="-R .comment -R .GCC.command.line -R .note.gnu.gold-version"
- SPLIT_STRIP_FLAGS=
- ;;
-esac
-: ${PORTAGE_STRIP_FLAGS=${SAFE_STRIP_FLAGS} ${DEF_STRIP_FLAGS}}
-
-prepstrip_sources_dir=${EPREFIX}/usr/src/debug/${CATEGORY}/${PF}
-
-debugedit=$(type -P debugedit)
-if [[ -z ${debugedit} ]]; then
- debugedit_paths=(
- "${EPREFIX}/usr/libexec/rpm/debugedit"
- )
- for x in "${debugedit_paths[@]}"; do
- if [[ -x ${x} ]]; then
- debugedit=${x}
- break
- fi
- done
-fi
-[[ ${debugedit} ]] && debugedit_found=true || debugedit_found=false
-debugedit_warned=false
-
-__multijob_init
-
-# Setup $T filesystem layout that we care about.
-tmpdir="${T}/prepstrip"
-rm -rf "${tmpdir}"
-mkdir -p "${tmpdir}"/{inodes,splitdebug,sources}
-
-# Usage: save_elf_sources <elf>
-save_elf_sources() {
- ${FEATURES_installsources} || return 0
- ${RESTRICT_installsources} && return 0
- if ! ${debugedit_found} ; then
- if ! ${debugedit_warned} ; then
- debugedit_warned=true
- ewarn "FEATURES=installsources is enabled but the debugedit binary could not be"
- ewarn "found. This feature will not work unless debugedit or rpm is installed!"
- fi
- return 0
- fi
-
- local x=$1
-
- # since we're editing the ELF here, we should recompute the build-id
- # (the -i flag below). save that output so we don't need to recompute
- # it later on in the save_elf_debug step.
- buildid=$("${debugedit}" -i \
- -b "${WORKDIR}" \
- -d "${prepstrip_sources_dir}" \
- -l "${tmpdir}/sources/${x##*/}.${BASHPID:-$(__bashpid)}" \
- "${x}")
-}
-
-# Usage: save_elf_debug <elf> [splitdebug file]
-save_elf_debug() {
- ${FEATURES_splitdebug} || return 0
- ${RESTRICT_splitdebug} && return 0
-
- # NOTE: Debug files must be installed in
- # ${EPREFIX}/usr/lib/debug/${EPREFIX} (note that ${EPREFIX} occurs
- # twice in this path) in order for gdb's debug-file-directory
- # lookup to work correctly.
- local x=$1
- local inode_debug=$2
- local splitdebug=$3
- local d_noslash=${D%/}
- local y=${ED%/}/usr/lib/debug/${x:${#d_noslash}}.debug
-
- # dont save debug info twice
- [[ ${x} == *".debug" ]] && return 0
-
- mkdir -p "${y%/*}"
-
- if [ -f "${inode_debug}" ] ; then
- ln "${inode_debug}" "${y}" || die "ln failed unexpectedly"
- else
- if [[ -n ${splitdebug} ]] ; then
- mv "${splitdebug}" "${y}"
- else
- local objcopy_flags="--only-keep-debug"
- ${FEATURES_compressdebug} && objcopy_flags+=" --compress-debug-sections"
- ${OBJCOPY} ${objcopy_flags} "${x}" "${y}"
- ${OBJCOPY} --add-gnu-debuglink="${y}" "${x}"
- fi
- # Only do the following if the debug file was
- # successfully created (see bug #446774).
- if [ $? -eq 0 ] ; then
- local args="a-x,o-w"
- [[ -g ${x} || -u ${x} ]] && args+=",go-r"
- chmod ${args} "${y}"
- ln "${y}" "${inode_debug}" || die "ln failed unexpectedly"
- fi
- fi
-
- # if we don't already have build-id from debugedit, look it up
- if [[ -z ${buildid} ]] ; then
- # convert the readelf output to something useful
- buildid=$(${READELF} -n "${x}" 2>/dev/null | awk '/Build ID:/{ print $NF; exit }')
- fi
- if [[ -n ${buildid} ]] ; then
- local buildid_dir="${ED%/}/usr/lib/debug/.build-id/${buildid:0:2}"
- local buildid_file="${buildid_dir}/${buildid:2}"
- mkdir -p "${buildid_dir}"
- [ -L "${buildid_file}".debug ] || ln -s "../../${x:${#D}}.debug" "${buildid_file}.debug"
- [ -L "${buildid_file}" ] || ln -s "/${x:${#D}}" "${buildid_file}"
- fi
-}
-
-# Usage: process_elf <elf>
-process_elf() {
- local x=$1 inode_link=$2 strip_flags=${*:3}
- local already_stripped lockfile xt_data
-
- __vecho " ${x:${#ED}}"
-
- # If two processes try to debugedit or strip the same hardlink at the
- # same time, it may corrupt files or cause loss of splitdebug info.
- # So, use a lockfile to prevent interference (easily observed with
- # dev-vcs/git which creates ~111 hardlinks to one file in
- # /usr/libexec/git-core).
- lockfile=${inode_link}_lockfile
- if ! ln "${inode_link}" "${lockfile}" 2>/dev/null ; then
- while [[ -f ${lockfile} ]] ; do
- sleep 1
- done
- unset lockfile
- fi
-
- [ -f "${inode_link}_stripped" ] && already_stripped=true || already_stripped=false
-
- if ! ${already_stripped} ; then
- if ${PRESERVE_XATTR} ; then
- xt_data=$(dump_xattrs "${x}")
- fi
- save_elf_sources "${x}"
- fi
-
- if ${strip_this} ; then
-
- # see if we can split & strip at the same time
- if [[ -n ${SPLIT_STRIP_FLAGS} ]] ; then
- local shortname="${x##*/}.debug"
- local splitdebug="${tmpdir}/splitdebug/${shortname}.${BASHPID:-$(__bashpid)}"
- ${already_stripped} || \
- ${STRIP} ${strip_flags} \
- -f "${splitdebug}" \
- -F "${shortname}" \
- "${x}"
- save_elf_debug "${x}" "${inode_link}_debug" "${splitdebug}"
- else
- save_elf_debug "${x}" "${inode_link}_debug"
- ${already_stripped} || \
- ${STRIP} ${strip_flags} "${x}"
- fi
- fi
-
- if ${already_stripped} ; then
- rm -f "${x}" || die "rm failed unexpectedly"
- ln "${inode_link}_stripped" "${x}" || die "ln failed unexpectedly"
- else
- ln "${x}" "${inode_link}_stripped" || die "ln failed unexpectedly"
- if [[ ${xt_data} ]] ; then
- restore_xattrs <<< "${xt_data}"
- fi
- fi
-
- [[ -n ${lockfile} ]] && rm -f "${lockfile}"
-}
-
-# The existance of the section .symtab tells us that a binary is stripped.
-# We want to log already stripped binaries, as this may be a QA violation.
-# They prevent us from getting the splitdebug data.
-if ! ${RESTRICT_binchecks} && ! ${RESTRICT_strip} ; then
- # We need to do the non-stripped scan serially first before we turn around
- # and start stripping the files ourselves. The log parsing can be done in
- # parallel though.
- log=${tmpdir}/scanelf-already-stripped.log
- scanelf -yqRBF '#k%F' -k '!.symtab' "$@" | sed -e "s#^${ED%/}/##" > "${log}"
- (
- __multijob_child_init
- qa_var="QA_PRESTRIPPED_${ARCH/-/_}"
- [[ -n ${!qa_var} ]] && QA_PRESTRIPPED="${!qa_var}"
- if [[ -n ${QA_PRESTRIPPED} && -s ${log} && \
- ${QA_STRICT_PRESTRIPPED-unset} = unset ]] ; then
- shopts=$-
- set -o noglob
- for x in ${QA_PRESTRIPPED} ; do
- sed -e "s#^${x#/}\$##" -i "${log}"
- done
- set +o noglob
- set -${shopts}
- fi
- sed -e "/^\$/d" -e "s#^#/#" -i "${log}"
- if [[ -s ${log} ]] ; then
- __vecho -e "\n"
- eqawarn "QA Notice: Pre-stripped files found:"
- eqawarn "$(<"${log}")"
- else
- rm -f "${log}"
- fi
- ) &
- __multijob_post_fork
-fi
-
-# Since strip creates a new inode, we need to know the initial set of
-# inodes in advance, so that we can avoid interference due to trying
-# to strip the same (hardlinked) file multiple times in parallel.
-# See bug #421099.
-if [[ ${USERLAND} == BSD ]] ; then
- get_inode_number() { stat -f '%i' "$1"; }
-else
- get_inode_number() { stat -c '%i' "$1"; }
-fi
-cd "${tmpdir}/inodes" || die "cd failed unexpectedly"
-while read -r x ; do
- inode_link=$(get_inode_number "${x}") || die "stat failed unexpectedly"
- echo "${x}" >> "${inode_link}" || die "echo failed unexpectedly"
-done < <(
- # Use sort -u to eliminate duplicates for bug #445336.
- (
- scanelf -yqRBF '#k%F' -k '.symtab' "$@"
- find "$@" -type f ! -type l -name '*.a'
- ) | LC_ALL=C sort -u
-)
-
-# Now we look for unstripped binaries.
-for inode_link in $(shopt -s nullglob; echo *) ; do
-while read -r x
-do
-
- if ! ${banner} ; then
- __vecho "strip: ${STRIP} ${PORTAGE_STRIP_FLAGS}"
- banner=true
- fi
-
- (
- __multijob_child_init
- f=$(file "${x}") || exit 0
- [[ -z ${f} ]] && exit 0
-
- if ! ${SKIP_STRIP} ; then
- # The noglob funk is to support STRIP_MASK="/*/booga" and to keep
- # the for loop from expanding the globs.
- # The eval echo is to support STRIP_MASK="/*/{booga,bar}" sex.
- set -o noglob
- strip_this=true
- for m in $(eval echo ${STRIP_MASK}) ; do
- [[ /${x#${ED%/}} == ${m} ]] && strip_this=false && break
- done
- set +o noglob
- else
- strip_this=false
- fi
-
- # In Prefix we are usually an unprivileged user, so we can't strip
- # unwritable objects. Make them temporarily writable for the
- # stripping.
- was_not_writable=false
- if [[ ! -w ${x} ]] ; then
- was_not_writable=true
- chmod u+w "${x}"
- fi
-
- # only split debug info for final linked objects
- # or kernel modules as debuginfo for intermediatary
- # files (think crt*.o from gcc/glibc) is useless and
- # actually causes problems. install sources for all
- # elf types though cause that stuff is good.
-
- buildid=
- if [[ ${f} == *"current ar archive"* ]] ; then
- __vecho " ${x:${#ED}}"
- if ${strip_this} ; then
- # If we have split debug enabled, then do not strip this.
- # There is no concept of splitdebug for objects not yet
- # linked in (only for finally linked ELFs), so we have to
- # retain the debug info in the archive itself.
- if ! ${FEATURES_splitdebug} || ${RESTRICT_splitdebug} ; then
- ${STRIP} -g "${x}"
- fi
- fi
- elif [[ ${f} == *"SB executable"* || ${f} == *"SB shared object"* ]] ; then
- process_elf "${x}" "${inode_link}" ${PORTAGE_STRIP_FLAGS}
- elif [[ ${f} == *"SB relocatable"* ]] ; then
- process_elf "${x}" "${inode_link}" ${SAFE_STRIP_FLAGS}
- fi
-
- if ${was_not_writable} ; then
- chmod u-w "${x}"
- fi
- ) &
- __multijob_post_fork
-
-done < "${inode_link}"
-done
-
-# With a bit more work, we could run the rsync processes below in
-# parallel, but not sure that'd be an overall improvement.
-__multijob_finish
-
-cd "${tmpdir}"/sources/ && cat * > "${tmpdir}/debug.sources" 2>/dev/null
-if [[ -s ${tmpdir}/debug.sources ]] && \
- ${FEATURES_installsources} && \
- ! ${RESTRICT_installsources} && \
- ${debugedit_found}
-then
- __vecho "installsources: rsyncing source files"
- [[ -d ${D%/}/${prepstrip_sources_dir#/} ]] || mkdir -p "${D%/}/${prepstrip_sources_dir#/}"
- grep -zv '/<[^/>]*>$' "${tmpdir}"/debug.sources | \
- (cd "${WORKDIR}"; LANG=C sort -z -u | \
- rsync -tL0 --chmod=ugo-st,a+r,go-w,Da+x,Fa-x --files-from=- "${WORKDIR}/" "${D%/}/${prepstrip_sources_dir#/}/" )
-
- # Preserve directory structure.
- # Needed after running save_elf_sources.
- # https://bugzilla.redhat.com/show_bug.cgi?id=444310
- while read -r -d $'\0' emptydir
- do
- >> "${emptydir}"/.keepdir
- done < <(find "${D%/}/${prepstrip_sources_dir#/}/" -type d -empty -print0)
-fi
-
-cd "${T}"
-rm -rf "${tmpdir}"
+exec -a "${0}" "${PORTAGE_BIN_PATH}"/estrip "${@}"
diff --git a/bin/estrip b/bin/estrip
new file mode 100755
index 000000000..2136e0d4d
--- /dev/null
+++ b/bin/estrip
@@ -0,0 +1,403 @@
+#!/bin/bash
+# Copyright 1999-2018 Gentoo Foundation
+# Distributed under the terms of the GNU General Public License v2
+
+source "${PORTAGE_BIN_PATH}"/helper-functions.sh || exit 1
+
+# avoid multiple calls to `has`. this creates things like:
+# FEATURES_foo=false
+# if "foo" is not in $FEATURES
+tf() { "$@" && echo true || echo false ; }
+exp_tf() {
+ local flag var=$1
+ shift
+ for flag in "$@" ; do
+ eval ${var}_${flag}=$(tf has ${flag} ${!var})
+ done
+}
+exp_tf FEATURES compressdebug installsources nostrip splitdebug xattr
+exp_tf RESTRICT binchecks installsources splitdebug strip
+
+if ! ___eapi_has_prefix_variables; then
+ EPREFIX= ED=${D}
+fi
+
+banner=false
+SKIP_STRIP=false
+if ${RESTRICT_strip} || ${FEATURES_nostrip} ; then
+ SKIP_STRIP=true
+ banner=true
+ ${FEATURES_installsources} || exit 0
+fi
+
+PRESERVE_XATTR=false
+if [[ ${KERNEL} == linux ]] && ${FEATURES_xattr} ; then
+ PRESERVE_XATTR=true
+ if type -P getfattr >/dev/null && type -P setfattr >/dev/null ; then
+ dump_xattrs() {
+ getfattr -d -m - --absolute-names "$1"
+ }
+ restore_xattrs() {
+ setfattr --restore=-
+ }
+ else
+ dump_xattrs() {
+ PYTHONPATH=${PORTAGE_PYTHONPATH:-${PORTAGE_PYM_PATH}} \
+ "${PORTAGE_PYTHON:-/usr/bin/python}" \
+ "${PORTAGE_BIN_PATH}/xattr-helper.py" --dump < <(echo -n "$1")
+ }
+ restore_xattrs() {
+ PYTHONPATH=${PORTAGE_PYTHONPATH:-${PORTAGE_PYM_PATH}} \
+ "${PORTAGE_PYTHON:-/usr/bin/python}" \
+ "${PORTAGE_BIN_PATH}/xattr-helper.py" --restore
+ }
+ fi
+fi
+
+# look up the tools we might be using
+for t in STRIP:strip OBJCOPY:objcopy READELF:readelf ; do
+ v=${t%:*} # STRIP
+ t=${t#*:} # strip
+ eval ${v}=\"${!v:-${CHOST}-${t}}\"
+ type -P -- ${!v} >/dev/null || eval ${v}=${t}
+done
+
+# Figure out what tool set we're using to strip stuff
+unset SAFE_STRIP_FLAGS DEF_STRIP_FLAGS SPLIT_STRIP_FLAGS
+case $(${STRIP} --version 2>/dev/null) in
+*elfutils*) # dev-libs/elfutils
+ # elfutils default behavior is always safe, so don't need to specify
+ # any flags at all
+ SAFE_STRIP_FLAGS=""
+ DEF_STRIP_FLAGS="--remove-comment"
+ SPLIT_STRIP_FLAGS="-f"
+ ;;
+*GNU*) # sys-devel/binutils
+ # We'll leave out -R .note for now until we can check out the relevance
+ # of the section when it has the ALLOC flag set on it ...
+ SAFE_STRIP_FLAGS="--strip-unneeded"
+ DEF_STRIP_FLAGS="-R .comment -R .GCC.command.line -R .note.gnu.gold-version"
+ SPLIT_STRIP_FLAGS=
+ ;;
+esac
+: ${PORTAGE_STRIP_FLAGS=${SAFE_STRIP_FLAGS} ${DEF_STRIP_FLAGS}}
+
+prepstrip_sources_dir=${EPREFIX}/usr/src/debug/${CATEGORY}/${PF}
+
+debugedit=$(type -P debugedit)
+if [[ -z ${debugedit} ]]; then
+ debugedit_paths=(
+ "${EPREFIX}/usr/libexec/rpm/debugedit"
+ )
+ for x in "${debugedit_paths[@]}"; do
+ if [[ -x ${x} ]]; then
+ debugedit=${x}
+ break
+ fi
+ done
+fi
+[[ ${debugedit} ]] && debugedit_found=true || debugedit_found=false
+debugedit_warned=false
+
+__multijob_init
+
+# Setup $T filesystem layout that we care about.
+tmpdir="${T}/prepstrip"
+rm -rf "${tmpdir}"
+mkdir -p "${tmpdir}"/{inodes,splitdebug,sources}
+
+# Usage: save_elf_sources <elf>
+save_elf_sources() {
+ ${FEATURES_installsources} || return 0
+ ${RESTRICT_installsources} && return 0
+ if ! ${debugedit_found} ; then
+ if ! ${debugedit_warned} ; then
+ debugedit_warned=true
+ ewarn "FEATURES=installsources is enabled but the debugedit binary could not be"
+ ewarn "found. This feature will not work unless debugedit or rpm is installed!"
+ fi
+ return 0
+ fi
+
+ local x=$1
+
+ # since we're editing the ELF here, we should recompute the build-id
+ # (the -i flag below). save that output so we don't need to recompute
+ # it later on in the save_elf_debug step.
+ buildid=$("${debugedit}" -i \
+ -b "${WORKDIR}" \
+ -d "${prepstrip_sources_dir}" \
+ -l "${tmpdir}/sources/${x##*/}.${BASHPID:-$(__bashpid)}" \
+ "${x}")
+}
+
+# Usage: save_elf_debug <elf> [splitdebug file]
+save_elf_debug() {
+ ${FEATURES_splitdebug} || return 0
+ ${RESTRICT_splitdebug} && return 0
+
+ # NOTE: Debug files must be installed in
+ # ${EPREFIX}/usr/lib/debug/${EPREFIX} (note that ${EPREFIX} occurs
+ # twice in this path) in order for gdb's debug-file-directory
+ # lookup to work correctly.
+ local x=$1
+ local inode_debug=$2
+ local splitdebug=$3
+ local d_noslash=${D%/}
+ local y=${ED%/}/usr/lib/debug/${x:${#d_noslash}}.debug
+
+ # dont save debug info twice
+ [[ ${x} == *".debug" ]] && return 0
+
+ mkdir -p "${y%/*}"
+
+ if [ -f "${inode_debug}" ] ; then
+ ln "${inode_debug}" "${y}" || die "ln failed unexpectedly"
+ else
+ if [[ -n ${splitdebug} ]] ; then
+ mv "${splitdebug}" "${y}"
+ else
+ local objcopy_flags="--only-keep-debug"
+ ${FEATURES_compressdebug} && objcopy_flags+=" --compress-debug-sections"
+ ${OBJCOPY} ${objcopy_flags} "${x}" "${y}"
+ ${OBJCOPY} --add-gnu-debuglink="${y}" "${x}"
+ fi
+ # Only do the following if the debug file was
+ # successfully created (see bug #446774).
+ if [ $? -eq 0 ] ; then
+ local args="a-x,o-w"
+ [[ -g ${x} || -u ${x} ]] && args+=",go-r"
+ chmod ${args} "${y}"
+ ln "${y}" "${inode_debug}" || die "ln failed unexpectedly"
+ fi
+ fi
+
+ # if we don't already have build-id from debugedit, look it up
+ if [[ -z ${buildid} ]] ; then
+ # convert the readelf output to something useful
+ buildid=$(${READELF} -n "${x}" 2>/dev/null | awk '/Build ID:/{ print $NF; exit }')
+ fi
+ if [[ -n ${buildid} ]] ; then
+ local buildid_dir="${ED%/}/usr/lib/debug/.build-id/${buildid:0:2}"
+ local buildid_file="${buildid_dir}/${buildid:2}"
+ mkdir -p "${buildid_dir}"
+ [ -L "${buildid_file}".debug ] || ln -s "../../${x:${#D}}.debug" "${buildid_file}.debug"
+ [ -L "${buildid_file}" ] || ln -s "/${x:${#D}}" "${buildid_file}"
+ fi
+}
+
+# Usage: process_elf <elf>
+process_elf() {
+ local x=$1 inode_link=$2 strip_flags=${*:3}
+ local already_stripped lockfile xt_data
+
+ __vecho " ${x:${#ED}}"
+
+ # If two processes try to debugedit or strip the same hardlink at the
+ # same time, it may corrupt files or cause loss of splitdebug info.
+ # So, use a lockfile to prevent interference (easily observed with
+ # dev-vcs/git which creates ~111 hardlinks to one file in
+ # /usr/libexec/git-core).
+ lockfile=${inode_link}_lockfile
+ if ! ln "${inode_link}" "${lockfile}" 2>/dev/null ; then
+ while [[ -f ${lockfile} ]] ; do
+ sleep 1
+ done
+ unset lockfile
+ fi
+
+ [ -f "${inode_link}_stripped" ] && already_stripped=true || already_stripped=false
+
+ if ! ${already_stripped} ; then
+ if ${PRESERVE_XATTR} ; then
+ xt_data=$(dump_xattrs "${x}")
+ fi
+ save_elf_sources "${x}"
+ fi
+
+ if ${strip_this} ; then
+
+ # see if we can split & strip at the same time
+ if [[ -n ${SPLIT_STRIP_FLAGS} ]] ; then
+ local shortname="${x##*/}.debug"
+ local splitdebug="${tmpdir}/splitdebug/${shortname}.${BASHPID:-$(__bashpid)}"
+ ${already_stripped} || \
+ ${STRIP} ${strip_flags} \
+ -f "${splitdebug}" \
+ -F "${shortname}" \
+ "${x}"
+ save_elf_debug "${x}" "${inode_link}_debug" "${splitdebug}"
+ else
+ save_elf_debug "${x}" "${inode_link}_debug"
+ ${already_stripped} || \
+ ${STRIP} ${strip_flags} "${x}"
+ fi
+ fi
+
+ if ${already_stripped} ; then
+ rm -f "${x}" || die "rm failed unexpectedly"
+ ln "${inode_link}_stripped" "${x}" || die "ln failed unexpectedly"
+ else
+ ln "${x}" "${inode_link}_stripped" || die "ln failed unexpectedly"
+ if [[ ${xt_data} ]] ; then
+ restore_xattrs <<< "${xt_data}"
+ fi
+ fi
+
+ [[ -n ${lockfile} ]] && rm -f "${lockfile}"
+}
+
+# The existance of the section .symtab tells us that a binary is stripped.
+# We want to log already stripped binaries, as this may be a QA violation.
+# They prevent us from getting the splitdebug data.
+if ! ${RESTRICT_binchecks} && ! ${RESTRICT_strip} ; then
+ # We need to do the non-stripped scan serially first before we turn around
+ # and start stripping the files ourselves. The log parsing can be done in
+ # parallel though.
+ log=${tmpdir}/scanelf-already-stripped.log
+ scanelf -yqRBF '#k%F' -k '!.symtab' "$@" | sed -e "s#^${ED%/}/##" > "${log}"
+ (
+ __multijob_child_init
+ qa_var="QA_PRESTRIPPED_${ARCH/-/_}"
+ [[ -n ${!qa_var} ]] && QA_PRESTRIPPED="${!qa_var}"
+ if [[ -n ${QA_PRESTRIPPED} && -s ${log} && \
+ ${QA_STRICT_PRESTRIPPED-unset} = unset ]] ; then
+ shopts=$-
+ set -o noglob
+ for x in ${QA_PRESTRIPPED} ; do
+ sed -e "s#^${x#/}\$##" -i "${log}"
+ done
+ set +o noglob
+ set -${shopts}
+ fi
+ sed -e "/^\$/d" -e "s#^#/#" -i "${log}"
+ if [[ -s ${log} ]] ; then
+ __vecho -e "\n"
+ eqawarn "QA Notice: Pre-stripped files found:"
+ eqawarn "$(<"${log}")"
+ else
+ rm -f "${log}"
+ fi
+ ) &
+ __multijob_post_fork
+fi
+
+# Since strip creates a new inode, we need to know the initial set of
+# inodes in advance, so that we can avoid interference due to trying
+# to strip the same (hardlinked) file multiple times in parallel.
+# See bug #421099.
+if [[ ${USERLAND} == BSD ]] ; then
+ get_inode_number() { stat -f '%i' "$1"; }
+else
+ get_inode_number() { stat -c '%i' "$1"; }
+fi
+cd "${tmpdir}/inodes" || die "cd failed unexpectedly"
+while read -r x ; do
+ inode_link=$(get_inode_number "${x}") || die "stat failed unexpectedly"
+ echo "${x}" >> "${inode_link}" || die "echo failed unexpectedly"
+done < <(
+ # Use sort -u to eliminate duplicates for bug #445336.
+ (
+ scanelf -yqRBF '#k%F' -k '.symtab' "$@"
+ find "$@" -type f ! -type l -name '*.a'
+ ) | LC_ALL=C sort -u
+)
+
+# Now we look for unstripped binaries.
+for inode_link in $(shopt -s nullglob; echo *) ; do
+while read -r x
+do
+
+ if ! ${banner} ; then
+ __vecho "strip: ${STRIP} ${PORTAGE_STRIP_FLAGS}"
+ banner=true
+ fi
+
+ (
+ __multijob_child_init
+ f=$(file "${x}") || exit 0
+ [[ -z ${f} ]] && exit 0
+
+ if ! ${SKIP_STRIP} ; then
+ # The noglob funk is to support STRIP_MASK="/*/booga" and to keep
+ # the for loop from expanding the globs.
+ # The eval echo is to support STRIP_MASK="/*/{booga,bar}" sex.
+ set -o noglob
+ strip_this=true
+ for m in $(eval echo ${STRIP_MASK}) ; do
+ [[ /${x#${ED%/}} == ${m} ]] && strip_this=false && break
+ done
+ set +o noglob
+ else
+ strip_this=false
+ fi
+
+ # In Prefix we are usually an unprivileged user, so we can't strip
+ # unwritable objects. Make them temporarily writable for the
+ # stripping.
+ was_not_writable=false
+ if [[ ! -w ${x} ]] ; then
+ was_not_writable=true
+ chmod u+w "${x}"
+ fi
+
+ # only split debug info for final linked objects
+ # or kernel modules as debuginfo for intermediatary
+ # files (think crt*.o from gcc/glibc) is useless and
+ # actually causes problems. install sources for all
+ # elf types though cause that stuff is good.
+
+ buildid=
+ if [[ ${f} == *"current ar archive"* ]] ; then
+ __vecho " ${x:${#ED}}"
+ if ${strip_this} ; then
+ # If we have split debug enabled, then do not strip this.
+ # There is no concept of splitdebug for objects not yet
+ # linked in (only for finally linked ELFs), so we have to
+ # retain the debug info in the archive itself.
+ if ! ${FEATURES_splitdebug} || ${RESTRICT_splitdebug} ; then
+ ${STRIP} -g "${x}"
+ fi
+ fi
+ elif [[ ${f} == *"SB executable"* || ${f} == *"SB shared object"* ]] ; then
+ process_elf "${x}" "${inode_link}" ${PORTAGE_STRIP_FLAGS}
+ elif [[ ${f} == *"SB relocatable"* ]] ; then
+ process_elf "${x}" "${inode_link}" ${SAFE_STRIP_FLAGS}
+ fi
+
+ if ${was_not_writable} ; then
+ chmod u-w "${x}"
+ fi
+ ) &
+ __multijob_post_fork
+
+done < "${inode_link}"
+done
+
+# With a bit more work, we could run the rsync processes below in
+# parallel, but not sure that'd be an overall improvement.
+__multijob_finish
+
+cd "${tmpdir}"/sources/ && cat * > "${tmpdir}/debug.sources" 2>/dev/null
+if [[ -s ${tmpdir}/debug.sources ]] && \
+ ${FEATURES_installsources} && \
+ ! ${RESTRICT_installsources} && \
+ ${debugedit_found}
+then
+ __vecho "installsources: rsyncing source files"
+ [[ -d ${D%/}/${prepstrip_sources_dir#/} ]] || mkdir -p "${D%/}/${prepstrip_sources_dir#/}"
+ grep -zv '/<[^/>]*>$' "${tmpdir}"/debug.sources | \
+ (cd "${WORKDIR}"; LANG=C sort -z -u | \
+ rsync -tL0 --chmod=ugo-st,a+r,go-w,Da+x,Fa-x --files-from=- "${WORKDIR}/" "${D%/}/${prepstrip_sources_dir#/}/" )
+
+ # Preserve directory structure.
+ # Needed after running save_elf_sources.
+ # https://bugzilla.redhat.com/show_bug.cgi?id=444310
+ while read -r -d $'\0' emptydir
+ do
+ >> "${emptydir}"/.keepdir
+ done < <(find "${D%/}/${prepstrip_sources_dir#/}/" -type d -empty -print0)
+fi
+
+cd "${T}"
+rm -rf "${tmpdir}"