#!/bin/sh # # Copyright (c) 2018-2020, Christer Edwards # All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions are met: # # * Redistributions of source code must retain the above copyright notice, this # list of conditions and the following disclaimer. # # * Redistributions in binary form must reproduce the above copyright notice, # this list of conditions and the following disclaimer in the documentation # and/or other materials provided with the distribution. # # * Neither the name of the copyright holder nor the names of its # contributors may be used to endorse or promote products derived from # this software without specific prior written permission. # # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR # SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, # OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. PATH=${PATH}:/sbin:/bin:/usr/sbin:/usr/bin:/usr/local/sbin:/usr/local/bin . /usr/local/share/bastille/common.sh ## root check first. bastille_root_check() { if [ "$(id -u)" -ne 0 ]; then ## permission denied error_notify "Bastille: Permission Denied" error_exit "root / sudo / doas required" fi } bastille_root_check ## check for config existance bastille_conf_check() { if [ ! -r "/usr/local/etc/bastille/bastille.conf" ]; then error_exit "Missing Configuration" fi } bastille_conf_check ## we only load the config if conf_check passes . /usr/local/etc/bastille/bastille.conf ## bastille_prefix should be 0750 ## this restricts file system access to privileged users bastille_perms_check() { if [ -d "${bastille_prefix}" ]; then BASTILLE_PREFIX_PERMS=$(stat -f "%Op" "${bastille_prefix}") if [ "${BASTILLE_PREFIX_PERMS}" != 40750 ]; then error_notify "Insecure permissions on ${bastille_prefix}" error_exit "Try: chmod 0750 ${bastille_prefix}" fi fi } bastille_perms_check ## version BASTILLE_VERSION="0.7.20200714" usage() { cat << EOF Bastille is an open-source system for automating deployment and management of containerized applications on FreeBSD. Usage: bastille command TARGET [args] Available Commands: bootstrap Bootstrap a FreeBSD release for container base. cmd Execute arbitrary command on targeted container(s). clone Clone an existing container. console Console into a running container. convert Convert a Thin container into a Thick container. cp cp(1) files from host to targeted container(s). create Create a new thin container or a thick container if -T|--thick option specified. destroy Destroy a stopped container or a FreeBSD release. edit Edit container configuration files (advanced). export Exports a specified container. help Help about any command. htop Interactive process viewer (requires htop). import Import a specified container. list List containers (running and stopped). mount Mount a volume inside the targeted container(s). pkg Manipulate binary packages within targeted container(s). See pkg(8). rdr Redirect host port to container port. rename Rename a container. restart Restart a running container. service Manage services within targeted container(s). start Start a stopped container. stop Stop a running container. sysrc Safely edit rc files within targeted container(s). template Apply file templates to targeted container(s). top Display and update information about the top(1) cpu processes. umount Unmount a volume from within the targeted container(s). update Update container base -pX release. upgrade Upgrade container release to X.Y-RELEASE. verify Compare release against a "known good" index. zfs Manage (get|set) ZFS attributes on targeted container(s). Use "bastille -v|--version" for version information. Use "bastille command -h|--help" for more information about a command. EOF exit 1 } [ $# -lt 1 ] && usage CMD=$1 shift # Handle special-case commands first. case "${CMD}" in version|-v|--version) info "${BASTILLE_VERSION}" exit 0 ;; help|-h|--help) usage ;; bootstrap|create|destroy|import|list|rdr|restart|start|update|upgrade|verify) # Nothing "extra" to do for these commands. -- cwells ;; clone|cmd|console|convert|cp|edit|export|htop|limits|mount|pkg|rename|service|stop|sysrc|template|top|umount|zfs) # Parse the target and ensure it exists. -- cwells if [ $# -eq 0 ]; then # No target was given, so show the command's help. -- cwells PARAMS='help' elif [ "${1}" != 'help' ] && [ "${1}" != '-h' ] && [ "${1}" != '--help' ]; then TARGET="${1}" shift if [ "${TARGET}" = 'ALL' ]; then _JAILS=$(jls name) JAILS="" for _jail in ${_JAILS}; do _JAILPATH=$(jls -j "${_jail}" path) if [ -z ${_JAILPATH##${bastille_jailsdir}*} ]; then JAILS="${JAILS} ${_jail}" fi done else JAILS=$(jls name | awk "/^${TARGET}$/") # Ensure the target exists. -- cwells if [ ! -d "${bastille_jailsdir}/${TARGET}" ]; then error_exit "[${TARGET}]: Not found." fi case "${CMD}" in cmd|console|htop|pkg|service|stop|sysrc|template|top) # Require the target to be running. -- cwells if [ ! "$(jls name | awk "/^${TARGET}$/")" ]; then error_exit "[${TARGET}]: Not started. See 'bastille start ${TARGET}'." fi ;; convert|rename) # Require the target to be stopped. -- cwells if [ "$(jls name | awk "/^${TARGET}$/")" ]; then error_exit "${TARGET} is running. See 'bastille stop ${TARGET}'." fi ;; esac fi export TARGET export JAILS fi ;; *) # Filter out all non-commands usage ;; esac SCRIPTPATH="${bastille_sharedir}/${CMD}.sh" if [ -f "${SCRIPTPATH}" ]; then : "${UMASK:=022}" umask "${UMASK}" : "${SH:=sh}" if [ -n "${PARAMS}" ]; then exec "${SH}" "${SCRIPTPATH}" "${PARAMS}" else exec "${SH}" "${SCRIPTPATH}" "$@" fi else error_exit "${SCRIPTPATH} not found." fi