From: Daniel Lezcano Date: Sun, 27 Dec 2009 21:36:09 +0000 (+0100) Subject: cleanup lxc-debian script X-Git-Tag: lxc-0.6.5~49 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=fb7460fe60699b637bbb97b404e752284e755519;p=thirdparty%2Flxc.git cleanup lxc-debian script The lxc-debian is epurated and consolidated with a better error handling. This script is no longer interactive but it installs in a specified place the debian rootfs. This script is not supposed to be called directly so it will fall in libexec path very soon. This script is called by lxc-create as a template with the right option and the right place. The debian network configuration is by dhcp. Signed-off-by: Daniel Lezcano --- diff --git a/scripts/lxc-debian.in b/scripts/lxc-debian.in index ff9fe4d1c..fa7401344 100755 --- a/scripts/lxc-debian.in +++ b/scripts/lxc-debian.in @@ -1,48 +1,32 @@ #!/bin/bash -# set -ex - -CACHE="@LOCALSTATEDIR@/cache/lxc/debian" - -NAME="debian" -CONFFILE="lxc.conf" -MNTFILE= -TMPMNTFILE= -UTSNAME= -IPV4="172.20.0.21" -GATEWAY="172.20.0.1" -MTU="1500" - -# These paths are within the container so do not need to obey configure prefixes -INTERFACES="/etc/network/interfaces" -INITTAB="/etc/inittab" -HOSTNAME="/etc/hostname" -FSTAB="/etc/fstab" -SSHD_CONFIG="/etc/ssh/sshd_config" -PROFILE="/etc/profile" - -################################################################################ -# debian custom configuration files -################################################################################ - -# custom selinux - -write_debian_selinux() { - mkdir -p $ROOTFS/selinux - echo 0 > $ROOTFS/selinux/enforce -} -# custom fstab +# +# lxc: linux Container library -write_debian_fstab() { -cat < $ROOTFS/$FSTAB -tmpfs /dev/shm tmpfs defaults 0 0 -EOF -} +# Authors: +# Daniel Lezcano + +# This library is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. + +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# Lesser General Public License for more details. -# custom inittab +# You should have received a copy of the GNU Lesser General Public +# License along with this library; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -write_debian_inittab() { -cat < $ROOTFS/$INITTAB +configure_debian() +{ + rootfs=$1 + hostname=$2 + + # configure the inittab + cat < $rootfs/etc/inittab id:3:initdefault: si::sysinit:/etc/init.d/rcS l0:0:wait:/etc/init.d/rc 0 @@ -60,35 +44,13 @@ c2:12345:respawn:/sbin/getty 38400 tty2 linux c3:12345:respawn:/sbin/getty 38400 tty3 linux c4:12345:respawn:/sbin/getty 38400 tty4 linux EOF -} -# custom network configuration - -write_debian_network() { -cat < $ROOTFS/$INTERFACES -auto eth0 lo -iface eth0 inet static -address $IPV4 -netmask 255.255.255.0 -broadcast 0.0.0.0 -mtu $MTU -up route add default gw $GATEWAY -iface lo inet loopback -EOF -} - -# custom hostname - -write_debian_hostname() { -cat < $ROOTFS/$HOSTNAME -$UTSNAME -EOF -} + # disable selinux in debian + mkdir -p $rootfs/selinux + echo 0 > $rootfs/selinux/enforce -# custom sshd configuration file - -write_debian_sshd_config() { -cat < $ROOTFS/$SSHD_CONFIG + # by default setup root password with no password + cat < $rootfs/etc/ssh/sshd_config Port 22 Protocol 2 HostKey /etc/ssh/ssh_host_rsa_key @@ -109,317 +71,252 @@ HostbasedAuthentication no PermitEmptyPasswords yes ChallengeResponseAuthentication no EOF -} -reconfigure_debian_packages() { - chroot $ROOTFS /usr/sbin/dpkg-reconfigure locales -} - -disable_debian_services() { - chroot $ROOTFS /usr/sbin/update-rc.d -f umountfs remove - chroot $ROOTFS /usr/sbin/update-rc.d -f hwclock.sh remove - chroot $ROOTFS /usr/sbin/update-rc.d -f hwclockfirst.sh remove -} - - -################################################################################ -# lxc configuration files -################################################################################ + # configure the network using the dhcp + cat < $rootfs/etc/network/interfaces +auto lo +iface lo inet loopback -write_lxc_configuration() { -cat < $CONFFILE -lxc.utsname = $UTSNAME -lxc.tty = 4 -lxc.pts = 1024 -lxc.network.type = veth -lxc.network.flags = up -lxc.network.link = br0 -lxc.network.name = eth0 -lxc.network.mtu = $MTU -lxc.rootfs = $ROOTFS -lxc.cgroup.devices.deny = a -# /dev/null and zero -lxc.cgroup.devices.allow = c 1:3 rwm -lxc.cgroup.devices.allow = c 1:5 rwm -# consoles -lxc.cgroup.devices.allow = c 5:1 rwm -lxc.cgroup.devices.allow = c 5:0 rwm -lxc.cgroup.devices.allow = c 4:0 rwm -lxc.cgroup.devices.allow = c 4:1 rwm -# /dev/{,u}random -lxc.cgroup.devices.allow = c 1:9 rwm -lxc.cgroup.devices.allow = c 1:8 rwm -lxc.cgroup.devices.allow = c 136:* rwm -lxc.cgroup.devices.allow = c 5:2 rwm -# rtc -lxc.cgroup.devices.allow = c 254:0 rwm +auto eth0 +iface eth0 inet dhcp EOF - if [ ! -z "$TMPMNTFILE" ]; then - cat $TMPMNTFILE >> $CONFFILE - fi -} + # set the hostname + cat < $rootfs/etc/hostname +$hostname +EOF -write_lxc_mounts() { + # reconfigure some services + chroot $rootfs /usr/sbin/dpkg-reconfigure locales - if [ ! -z "$MNTFILE" ]; then - TMPMNTFILE=$(mktemp lxc.$NAME.XXXXXXXXXX) - sed -e 's/^\(.*\)/lxc.mount.entry=&/' $MNTFILE >$TMPMNTFILE - fi + # remove pointless services in a container + chroot $rootfs /usr/sbin/update-rc.d -f umountfs remove + chroot $rootfs /usr/sbin/update-rc.d -f hwclock.sh remove + chroot $rootfs /usr/sbin/update-rc.d -f hwclockfirst.sh remove } -collect_information() { - # choose a container name, default is 'debian' - echo -n "What is the name for the container ? [$NAME] " - read _NAME_ - - if [ ! -z "$_NAME_" ]; then - NAME=$_NAME_ - fi - - # choose a hostname, default is the container name - echo -n "What hostname do you wish for this container ? [$NAME] " - read _UTSNAME_ - - if [ ! -z "$_UTSNAME_" ]; then - UTSNAME=$_UTSNAME_ - else - UTSNAME=$NAME - fi - - # choose an ipv4 address, better to choose the same network than - # your host - echo -n "What IP address do you wish for this container ? [$IPV4] " - read _IPV4_ - - if [ ! -z "$_IPV4_" ]; then - IPV4=$_IPV4_ - fi - - # choose the gateway ip address - echo -n "What is the gateway IP address ? [$GATEWAY] " - read _GATEWAY_ - - if [ ! -z "$_GATEWAY_" ]; then - GATEWAY=$_GATEWAY_ - fi - - # choose the MTU size - echo -n "What is the MTU size ? [$MTU] " - read _MTU_ - - if [ ! -z "$_MTU_" ]; then - MTU=$_MTU_ +download_debian() +{ + packages=\ +ifupdown,\ +locales,\ +libui-dialog-perl,\ +dialog,\ +dhcp-client,\ +netbase,\ +net-tools,\ +iproute,\ +openssh-server + + cache=$1 + arch=$2 + + # check the mini debian was not already downloaded + mkdir -p "$cache/partial-$arch" + if [ $? -ne 0 ]; then + echo "Failed to create '$cache/partial-$arch' directory" + return 1 fi - ROOTFS="./rootfs.$NAME" - # choose the rootfs - echo -n "Specify the location of the rootfs [$ROOTFS] " - read _ROOTFS_ - - if [ ! -z "$_ROOTFS_" ]; then - ROOTFS=$_ROOTFS_ + # download a mini debian into a cache + echo "Downloading debian minimal ..." + debootstrap --verbose --variant=minbase --arch=$arch \ + --include $packages \ + lenny $cache/partial-$arch http://ftp.debian.org/debian + if [ $? -ne 0 ]; then + echo "Failed to download the rootfs, aborting." + return 1 fi - echo -n "Specify the location for an extra fstab file [(none)] " - read _MNTFILE_ + mv "$1/partial-$arch" "$1/rootfs-$arch" + echo "Download complete." - if [ ! -z "$_MNTFILE_" ]; then - MNTFILE=$_MNTFILE_ - fi + return 0 } -install_debian() +copy_debian() { - # check if the rootfs does already exist - if [ ! -e "$ROOTFS" ]; then - mkdir -p @LOCALSTATEDIR@/lock/subsys/ - ( - flock -n -x 200 - - - RES=$? - if [ "$RES" != "0" ]; then - echo "Cache repository is busy." - break - fi - - echo "Choose your architecture" - select ARCH in amd64 i386; do - echo "Architecture $ARCH selected" - break; - done - - # check the mini debian was not already downloaded - echo -n "Checking cache download ..." - if [ ! -e "$CACHE/rootfs-$ARCH" ]; then - - echo "not cached" - - mkdir -p "$CACHE/partial-$ARCH" - - # download a mini debian into a cache - echo "Downloading debian minimal ..." - debootstrap --verbose --variant=minbase --arch=$ARCH \ - --include ifupdown,locales,libui-dialog-perl,dialog,apache2,netbase,net-tools,iproute,openssh-server \ - lenny $CACHE/partial-$ARCH http://ftp.debian.org/debian - - RESULT=$? - if [ "$RESULT" != "0" ]; then - echo "Failed to download the rootfs, aborting." - exit 1 - fi - mv "$CACHE/partial-$ARCH" "$CACHE/rootfs-$ARCH" - echo "Download complete." - else - echo "Found." - fi - - # make a local copy of the minidebian - echo -n "Copying rootfs ..." - cp -a $CACHE/rootfs-$ARCH $ROOTFS && echo "Done." || exit - ) 200> "@LOCALSTATEDIR@/lock/subsys/lxc" - fi + cache=$1 + arch=$2 + rootfs=$3 + # make a local copy of the minidebian + echo -n "Copying rootfs to $rootfs..." + cp -a $cache/rootfs-$arch $rootfs || return 1 + return 0 } -create() { - - collect_information - - install_debian - - write_lxc_mounts - - write_lxc_configuration - - write_debian_inittab - - write_debian_hostname - - write_debian_fstab - - write_debian_network - - write_debian_sshd_config +install_debian() +{ + cache="@LOCALSTATEDIR@/cache/lxc/debian" + rootfs=$1 + mkdir -p @LOCALSTATEDIR@/lock/subsys/ + ( + flock -n -x 200 + if [ $? -ne 0 ]; then + echo "Cache repository is busy." + return 1 + fi - write_debian_selinux + arch=$(arch) + if [ "$arch" == "x86_64" ]; then + arch=amd64 + fi - reconfigure_debian_packages + if [ "$arch" == "i686" ]; then + arch=i386 + fi - disable_debian_services + echo "Checking cache download in $cache/rootfs-$arch ... " + if [ ! -e "$cache/rootfs-$arch" ]; then + download_debian $cache $arch + if [ $? -ne 0 ]; then + echo "Failed to download 'debian base'" + return 1 + fi + fi - @BINDIR@/lxc-create -n $NAME -f $CONFFILE - RES=$? + copy_debian $cache $arch $rootfs + if [ $? -ne 0 ]; then + echo "Failed to copy rootfs" + return 1 + fi - # remove the configuration files - rm -f $CONFFILE - rm -f $TMPMNTFILE + return 0 - if [ "$RES" != "0" ]; then - echo "Failed to create '$NAME'" - exit 1 - fi + ) 200>@LOCALSTATEDIR@/lock/subsys/lxc - echo "Done." - echo -e "\nYou can run your container with the 'lxc-start -n $NAME'\n" + return $? } -destroy() { - - echo -n "What is the name for the container ? [$NAME] " - read _NAME_ - - if [ ! -z "$_NAME_" ]; then - NAME=$_NAME_ - fi - - @BINDIR@/lxc-destroy -n $NAME - RETVAL=$? - if [ ! $RETVAL -eq 0 ]; then - echo "Failed to destroyed '$NAME'" - return $RETVAL; - fi +copy_configuration() +{ + path=$1 + rootfs=$2 + name=$3 - ROOTFS="./rootfs.$NAME" + cat <> $path/config +lxc.tty = 4 +lxc.pts = 1024 +lxc.rootfs = $rootfs +lxc.cgroup.devices.deny = a +# /dev/null and zero +lxc.cgroup.devices.allow = c 1:3 rwm +lxc.cgroup.devices.allow = c 1:5 rwm +# consoles +lxc.cgroup.devices.allow = c 5:1 rwm +lxc.cgroup.devices.allow = c 5:0 rwm +lxc.cgroup.devices.allow = c 4:0 rwm +lxc.cgroup.devices.allow = c 4:1 rwm +# /dev/{,u}random +lxc.cgroup.devices.allow = c 1:9 rwm +lxc.cgroup.devices.allow = c 1:8 rwm +lxc.cgroup.devices.allow = c 136:* rwm +lxc.cgroup.devices.allow = c 5:2 rwm +# rtc +lxc.cgroup.devices.allow = c 254:0 rwm +EOF - echo -n "Shall I remove the rootfs [y/n] ? " - read - if [ "$REPLY" = "y" ]; then - rm -rf $ROOTFS + if [ $? -ne 0 ]; then + echo "Failed to add configuration" + return 1 fi return 0 } -help() { - cat < "@LOCALSTATEDIR@/lock/subsys/lxc" + ) 200>@LOCALSTATEDIR@/lock/subsys/lxc } -if [ "$(id -u)" != "0" ]; then - echo "This script should be run as 'root'" +usage() +{ + cat < --clean +EOF + return 0 +} + +options=$(getopt -o hp:n:c -l help,path:,name:,clean -- "$@") +if [ $? -ne 0 ]; then + usage $(basename $0) exit 1 +fi +eval set -- "$options" + +while true +do + case "$1" in + -h|--help) usage $0 && exit 0;; + -p|--path) path=$2; shift 2;; + -n|--name) name=$2; shift 2;; + -c|--clean) clean=$2; shift 2;; + --) shift 1; break ;; + *) break ;; + esac +done + +if [ ! -z "$clean" -a -z "$path" ]; then + clean || exit 1 + exit 0 +fi + +type debootstrap +if [ $? -ne 0 ]; then + echo "'debootstrap' command is missing" + exit 1 +fi + +if [ -z "$path" ]; then + echo "'path' parameter is required" + exit 1 +fi + +if [ "$(id -u)" != "0" ]; then + echo "This script should be run as 'root'" + exit 1 fi -case "$1" in - create) - create;; - destroy) - destroy;; - help) - help;; - purge) - purge;; - *) - echo "Usage: $0 {create|destroy|purge|help}" - exit 1;; -esac +rootfs=$path/rootfs + +install_debian $rootfs +if [ $? -ne 0 ]; then + echo "failed to install debian" + exit 1 +fi + +configure_debian $rootfs $name +if [ $? -ne 0 ]; then + echo "failed to configure debian for a container" + exit 1 +fi + +copy_configuration $path $rootfs +if [ $? -ne 0 ]; then + echo "failed write configuration file" + exit 1 +fi + +if [ ! -z $clean ]; then + clean || exit 1 + exit 0 +fi