Created
June 21, 2023 15:26
-
-
Save indifferentcats/62f874f77bf44a482a1faabda00dd043 to your computer and use it in GitHub Desktop.
Linux script to auto-install packages for missing shared objects in binaries, typically ones downloaded from the Internet. This is a blind way to find and fix problems like those from chrome/chromedriver when it exits with code 127.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
my_uid=$(id -u) | |
if [ $my_uid -ne 0 ]; then | |
echo "WARNING: running as non-root. May not be able to install packages." | |
fi | |
HAS_APT=$(command -v apt) | |
HAS_DNF=$(command -v dnf) | |
HAS_YUM=$(command -v yum) | |
missing_packages_file=${MISSING_PACKAGES_FILE:-/tmp/list_of_missing_packages.txt} | |
function main() { | |
if [ -n "$HAS_APT" ]; then | |
echo "INFO: Found a debian-based distribution. Using apt-file." | |
fix_debian "$@" | |
elif [ -n "$HAS_DNF" ]; then | |
echo "INFO: Found an RPM-based distribution. Using dnf." | |
echo "WARNING: Finding packages with DNF is not yet supported." | |
exit 2 | |
elif [ -n "$HAS_YUM" ]; then | |
echo "INFO: Found an RPM-based distribution. Using yum." | |
fix_rpm_yum "$@" | |
else | |
echo "WARNING: No package manager found. Automatic fixing not supported." | |
exit 1 | |
fi | |
} | |
function fix_debian() { | |
apt_update | |
install_apt_file | |
libs=$(get_all_missing_libs "$@") | |
if [ -z "$libs" ]; then | |
echo "INFO: All dependant libraries found. No action." | |
return 0 | |
fi | |
echo "INFO: Found $(wc -l <<<"$libs") missing libraries" | |
echo "INFO: Missing libs:" $libs | |
packages=$(get_missing_deb $libs) | |
echo "INFO: Found $(wc -l <<<"$packages") missing packages" | |
if [ -n "$packages" ]; then | |
echo "INFO: Installing missing packages:" $packages | |
echo "$packages" >> $missing_packages_file | |
install_missing_deb $packages | |
fi | |
if [ -z "$packages" ] && [ -n "$libs" ]; then | |
echo "ERROR: The binaries are missing .so files, but no install packages could be found." | |
exit 1 | |
fi | |
uninstall_apt_file | |
apt_clean | |
echo "INFO: Checking our work" | |
libs=$(get_all_missing_libs "$@") | |
if [ -n "$libs" ]; then | |
echo "FAIL: The following libraries still did not get installed: $libs" | |
exit 2 | |
fi | |
echo "INFO: Success. All libraries were found for the executable(s): $@" | |
} | |
function fix_dnf() { | |
: | |
} | |
function fix_rpm_yum() { | |
libs="$(get_all_missing_libs "$@")" | |
if [ -z "$libs" ]; then | |
echo "INFO: All dependant libraries found. No action." | |
return 0 | |
fi | |
echo "INFO: Found $(wc -l <<<"$libs") missing libraries" | |
echo "INFO: Missing libs:" $libs | |
yum_install yum-utils | |
packages="$(get_missing_yum $libs | sed -e '/^[ ]*$/d')" | |
echo "INFO: Found $(echo "$packages" | wc -l ) missing packages" | |
if [ -n "$packages" ]; then | |
echo "INFO: Installing missing packages:" $packages | |
echo "$packages" >> $missing_packages_file | |
yum_install $packages | |
fi | |
if [ -z "$packages" ] && [ -n "$libs" ]; then | |
echo "ERROR: The binaries are missing .so files, but no install packages could be found." | |
exit 1 | |
fi | |
yum_remove yum-utils | |
yum_clean | |
echo "INFO: Checking our work" | |
libs=$(get_all_missing_libs "$@") | |
if [ -n "$libs" ]; then | |
echo "FAIL: The following libraries still did not get installed: $libs" | |
exit 2 | |
fi | |
echo "INFO: Success. All libraries were found for the executable(s): $@" | |
} | |
function get_all_missing_libs() { | |
for bin in "$@"; do | |
if [ -e "$bin" ] && [ -x "$bin" ]; then | |
/bin/ldd "$bin" | grep not\ found | sed -e 's/^[ \t]*//; s/ =>.*.//' | |
else | |
echo "ERROR: $bin does not exist or is not executable. Do not pass links." 1>&2 | |
return | |
fi | |
done | sort | uniq | |
} | |
function get_missing_deb() { | |
# some packages don't work well with others. | |
# liboss4-salsa-asound2 conflicts with libasound2 | |
debs_to_ignore="(liboss4-salsa-asound2)" | |
for lib in "$@"; do | |
apt-file search $lib 2>/dev/null | cut -f1 -d: | |
done | sort | uniq | grep -E -v -e '(firefox|thunderbird|chrome|chromium|-dev|-debug)' |\ | |
grep -E -v -e "$debs_to_ignore" | |
} | |
function get_missing_yum() { | |
for lib in "$@"; do | |
repoquery --whatprovides $lib --qf '%{NAME}' | head -1 | |
done | sort | uniq | |
} | |
function install_missing_deb() { | |
echo "INFO: installing packages " "$@" | |
show_on_error apt-get install -y "$@"; | |
} | |
function apt_update() { show_on_error apt-get update; } | |
function install_apt_file() { | |
show_on_error apt-get install -y apt-file; | |
show_on_error apt-file update; | |
} | |
function uninstall_apt_file() { show_on_error apt-get remove -y apt-file; } | |
function apt_clean() { show_on_error apt-get clean; } | |
function yum_install() { show_on_error yum install -y "$@"; } | |
function yum_remove() { show_on_error yum remove -y "$@"; } | |
function yum_clean() { show_on_error yum clean all; show_on_error rm -rf /var/cache/yum; } | |
function show_on_error() { | |
output=$("$@" 2>&1) | |
err=$? | |
if [ $err -ne 0 ]; then echo "$output"; fi | |
return $err | |
} | |
main "$@" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment