Skip to content

Instantly share code, notes, and snippets.

@fumiyas
Last active October 23, 2017 01:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fumiyas/787336abd6e2a8a62c8b9cd6b3cb62bc to your computer and use it in GitHub Desktop.
Save fumiyas/787336abd6e2a8a62c8b9cd6b3cb62bc to your computer and use it in GitHub Desktop.
#!/bin/ksh
##
## AIX ldd(1) clone with shared objects (*.so) in archives (*.a) support
## Copyright (C) 2017 SATOH Fumiyasu @ OSS Technology Corp, Japan
##
##
##
## License: GNU General Public License version 3
##
set -u
umask 0077
export PATH="/bin:/usr/bin"
export OBJECT_MODE=32_64
## ======================================================================
## Print arguments as-is
printr() {
print -r -- "$*"
}
ldd_executable() {
typeset executable
executable="$1"; shift
LC_ALL=C dump -H "$executable" \
|sed \
-e '1,/^INDEX *PATH /d' \
-e 's/^\(.\{7\}\) /\1-/' \
|{
typeset rpaths rpath
read -r n rpaths
typeset req_rpaths req_lib_name req_lib req_lib_obj req_lib_found req_lib_line
while read -r n req_rpaths req_lib_name req_lib_obj; do
[[ $req_rpaths == - ]] && req_rpaths="${LIBPATH:+$LIBPATH:}$rpaths"
req_lib_found=
for rpath in $(printr "$req_rpaths" |sed 's/:/ /g'); do
req_lib="${rpath%/}/$req_lib_name"
[[ -f $req_lib ]] || continue
if [[ -z $req_lib_obj ]]; then
req_lib_line="$req_lib"
else
req_lib_line="$req_lib($req_lib_obj)"
file "$req_lib" |grep ' archive ' >/dev/null || continue
## FIXME: Do recurive ldd
ar t "$req_lib" "$req_lib_obj" >/dev/null || continue
fi
printr " $req_lib_line"
req_lib_found=set
break
done
[[ -n $req_lib_found ]] || printr "Cannot find $req_lib_name" 1>&2
done
}
}
ldd_archive() {
typeset archive archive_obj
archive="$1"; shift
archive_obj="${1-}"
(
cd "$tmp_dir" || exit $?
if [[ $archive == /* ]]; then
ar x "$archive" ${archive_obj:+"$archive_obj"}
else
ar x "$OLDPWD/$archive" ${archive_obj:+"$archive_obj"}
fi
) || return $?
if [[ -n $archive_obj ]]; then
ldd_executable "$archive_obj"
rm "$archive_obj"
else
for archive_obj in "$tmp_dir"/*.o "$tmp_dir"/*.so*; do
[[ -f $archive_obj ]] || continue
ldd_executable "$archive_obj"
rm "$archive_obj"
done
fi
}
## ======================================================================
[[ $- == *x* ]] && typeset -ft $(typeset +f)
obj="$1"; shift
tmp_dir="/tmp/${0##*/}.$(date +%s).$$.tmp"
mkdir -m 0700 "$tmp_dir" || exit $?
trap 'rc=$?; rm -rf "$tmp_dir"; exit $rc' EXIT INT TERM
printr "$obj needs:"
if file "$obj" |grep ' executable ' >/dev/null; then
ldd_executable "$obj" || exit $?
else
ldd_archive "$obj" || exit $?
fi
exit 0
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment