Create chroot.sh

This commit is contained in:
Dryusdan 2021-03-15 17:59:45 +01:00
parent 560c57a0e9
commit c824302fce
1 changed files with 249 additions and 0 deletions

249
chroot.sh Normal file
View File

@ -0,0 +1,249 @@
#!/usr/bin/env bash
## Bash strict mode ####################################
set -o errexit # abort on nonzero exitstatus
set -o pipefail # don't hide errors within pipes
set -o nounset # abort on unbound variable
## Bash color ##########################################
# Set colors
RED='\033[0;31m'
GREEN='\033[00;32m'
YELLOW='\033[00;33m'
LRED='\033[01;31m'
LBLUE='\033[01;34m'
NC='\033[0m' # No Color
## Logs ################################################
readonly SCRIPTNAME="$(basename "$0")"
success() { echo -e "${GREEN}[SUCCESS] $* ${NC}" | logger --tag "${SCRIPTNAME}" --stderr; }
info() { echo -e "${LBLUE}[INFO] $* ${NC}" | logger --tag "${SCRIPTNAME}" --stderr ; }
warning() { echo -e "${YELLOW}[WARNING] $* ${NC}" | logger --tag "${SCRIPTNAME}" --stderr ; }
error() { echo -e "${LRED}[ERROR] $* ${NC}" | logger --tag "${SCRIPTNAME}" --stderr ; }
fatal() { echo -e "${RED}[FATAL] $* ${NC}" | logger --tag "${SCRIPTNAME}" --stderr ; exit 1 ; }
########################################################
## Define variables ###################################
LOCK="/var/lock/${SCRIPTNAME}.lock"
CHROOTPATH="/var/chroot"
ZONEINFO="/usr/share/zoneinfo"
libnss_dns="/lib/x86_64-linux-gnu/libnss_dns.so.2"
function _USAGE
{
cat << EOF
Usage :
${SCRIPTNAME} [OPTIONS]
Options :
--install Install chroot on ${WEBCHROOT}
--update Update configuration and binary on chroot
--configure Configure chroot for specific path
--help Display this help
EOF
exit 1
}
function _GET_OPTS
{
_SHORT_OPTS="i:u:c:h";
_LONG_OPTS="install,update,configure,help";
_OPTS=$(getopt \
-o "${_SHORT_OPTS}" \
-l "${_LONG_OPTS}" \
-n "${SCRIPTNAME}" -- "${@}")
if [ "${?}" -ne 0 ]
then
_USAGE
fi
eval set -- "${_OPTS}"
while true ; do
case "${1}" in
--install)
_INSTALL
shift
;;
--update)
_UPDATE
shift
;;
--configure)
_CONFIGURE "${3}"
shift 2
;;
--help)
_USAGE
shift
;;
*) echo "getopt Internal error!" ; exit 1 ;;
esac
done
}
function cpDep
{
if [[ -f "${CHROOTPATH}/${1}" ]]
then
error "$1 already exist in chroot"
return 1
fi
if [[ ! -d "${CHROOTPATH}/$(dirname "${1}")" ]]
then
mkdir -p "${CHROOTPATH}/$(dirname "${1}")"
fi
cp "${1}" "${CHROOTPATH}/${1}"
# Linked libraries
for DEP in $(ldd "${1}" | grep '=>' |cut -d'>' -f2 | awk '{print $1}')
do
if [[ ! -d "${CHROOTPATH}/$(dirname "${DEP}")" ]]
then
mkdir -p "${CHROOTPATH}/$(dirname "${DEP}")"
cp "${DEP}" "${CHROOTPATH}/${DEP}"
fi
done
# And lib64
for DEP in $(ldd bin/bash |grep lib64 | awk '{print $1}')
do
if [[ ! -d "${CHROOTPATH}/$(dirname "${DEP}")" ]]
then
mkdir -p "${CHROOTPATH}/$(dirname "${DEP}")"
fi
cp "${DEP}" "${CHROOTPATH}/${DEP}"
done
}
function _TIMEZONE
{
info "Clone Timezone"
if [[ ! -d "${CHROOTPATH}/${ZONEINFO}" ]]
then
mkdir -p "${CHROOTPATH}${ZONEINFO}"
rsync -azP "${ZONEINFO}/Europe" "${CHROOTPATH}${ZONEINFO}"
rsync -azP "${ZONEINFO}/UTC" "${CHROOTPATH}${ZONEINFO}"
rsync -azP "${ZONEINFO}/Etc" "${CHROOTPATH}${ZONEINFO}"
else
warning "Timezone already exist"
fi
}
function _ETC
{
info "Copy /etc"
if [[ ! -d "${CHROOTPATH}/etc" ]]
then
mkdir "${CHROOTPATH}/etc"
for conf in {ld.so.cache,resolv.conf,nsswitch.conf,passwd,group,hosts,networks,protocols,services,localtime}
do
cp "/etc/${conf}" "${CHROOTPATH}/etc/"
done
fi
}
function _DEV
{
info "Copy /dev"
if [[ ! -d "${CHROOTPATH}/dev" ]]
then
mkdir ${CHROOTPATH}/dev
mknod -m 666 "${CHROOTPATH}/dev/null" c 1 3
mknod -m 666 "${CHROOTPATH}/dev/zero" c 1 5
mknod -m 444 "${CHROOTPATH}/dev/random" c 1 8
mknod -m 444 "${CHROOTPATH}/dev/urandom" c 1 9
fi
}
function _LIBNSS
{
info "Copy libNSS"
if [[ ! -f ${CHROOTPATH}/${libnss_dns} ]]
then
mkdir -p "${CHROOTPATH}/$(dirname $libnss_dns)"
cp "$libnss_dns" "${CHROOTPATH}/$(dirname $libnss_dns)"
else
fatal "Error: Cant find important file libnss_dns.so.2 !"
fi
}
function _BIN
{
for binary in {/bin/bash,/bin/ls,/usr/bin/dig}
do
info "Copy ${binary} and dependencies"
cpDep "${binary}"
done
}
function _INSTALL
{
_TIMEZONE
_ETC
_DEV
_LIBNSS
_BIN
}
function _UPGRADE
{
_LIBNSS
_BIN
}
function _CONFIGURE
{
WEBCHROOT=${1}
info "Create /etc and /tmp"
mkdir -p "${WEBCHROOT}/etc"
mkdir -p "${WEBCHROOT}/tmp"
chmod 777 "${WEBCHROOT}/tmp"
info "Link system folder"
for chrooter in {dev,bin,lib/x86_64-linux-gnu,lib64,usr/bin,usr/lib/x86_64-linux-gnu/,usr/share/zoneinfo/Etc,usr/share/zoneinfo/Europe}
do
mkdir -p "${WEBCHROOT}/${chrooter}"
for binary in $(ls "${CHROOTPATH}/${chrooter}")
do
info "hardlink ${chrooter}/${binary}"
ln "${CHROOTPATH}/${chrooter}/${binary}" "${WEBCHROOT}/${chrooter}/${binary}"
done
done
info "hardlink libnss"
ln "${CHROOTPATH}/usr/share/zoneinfo/UTC" "${WEBCHROOT}/usr/share/zoneinfo/UTC"
info "hardlink some config"
for chrooter in {ld.so.cache,localtime,networks,nsswitch.conf,protocols,resolv.conf,services}
do
info "hardlink ${chrooter}"
ln "${CHROOTPATH}/etc/${chrooter}" "${WEBCHROOT}/etc/${chrooter}"
done
info "Copy some configurations"
for chrooter in {group,hosts,passwd}
do
info "Copy ${chrooter}"
cp "${CHROOTPATH}/etc/${chrooter}" "${WEBCHROOT}/etc/${chrooter}"
done
}
function _CLEAN
{
rm -f "${LOCK}"
}
if [[ ! -f "${LOCK}" ]]
then
trap _CLEAN EXIT
touch "${LOCK}"
_GET_OPTS "${@}"
_CLEAN
success "Account was successfull chrooted"
else
fatal "Lock already exist"
fi