Created
June 28, 2012 02:52
-
-
Save bobfeldbauer/3008518 to your computer and use it in GitHub Desktop.
Setup Linux container on debian
This file contains hidden or 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 | |
# | |
# lxc: linux Container library | |
# Authors: | |
# Daniel Lezcano <[email protected]> | |
# 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. | |
# 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 | |
path="/var/lib/lxc" | |
configure_debian() | |
{ | |
# disable selinux in debian | |
mkdir -p "$rootfs/selinux" | |
echo 0 > "$rootfs/selinux/enforce" | |
# configure the network | |
cat <<EOF > $rootfs/etc/network/interfaces | |
auto lo | |
iface lo inet loopback | |
auto eth0 | |
iface eth0 inet static | |
address 10.0.0.$num | |
netmask 255.255.255.0 | |
gateway 10.0.0.1 | |
EOF | |
# set the hostname | |
cat <<EOF > "$rootfs/etc/hostname" | |
$name | |
EOF | |
# configure resolver | |
cat <<EOF > "$rootfs/etc/resolv.conf" | |
nameserver 8.8.8.8 | |
EOF | |
# 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 | |
# Remove udev | |
chroot "$rootfs" /usr/bin/apt-get -y --purge remove udev | |
# Create tty device nodes | |
for num in $(seq 0 4); do | |
if [ ! -e "$rootfs/dev/tty$num" ]; then | |
mknod "$rootfs/dev/tty$num" c 4 $num | |
chmod 600 "$rootfs/dev/tty$num" | |
chown root:tty "$rootfs/dev/tty$num" | |
fi | |
done | |
echo "root:root" | chroot "$rootfs" chpasswd | |
echo "Root password is 'root', please change !" | |
return 0 | |
} | |
download_debian() | |
{ | |
packages="locales,less,vim,psmisc" | |
# check the mini debian was not already downloaded | |
mkdir -p "$cache/partial-$dist" | |
if [ $? -ne 0 ]; then | |
echo "Failed to create '$cache/partial-$dist' directory" | |
return 1 | |
fi | |
# download a mini debian into a cache | |
echo "Downloading debian minimal ..." | |
debootstrap --verbose --include "$packages" \ | |
"$dist" "$cache/partial-$dist" http://ftp.us.debian.org/debian | |
if [ $? -ne 0 ]; then | |
echo "Failed to download the rootfs, aborting." | |
return 1 | |
fi | |
mv "$cache/partial-$dist" "$cache/rootfs-$dist" | |
echo "Download complete." | |
return 0 | |
} | |
copy_debian() | |
{ | |
# make a local copy of the minidebian | |
echo -n "Copying rootfs to $rootfs..." | |
mkdir -p "$(dirname "$rootfs")" | |
cp -a "$cache/rootfs-$dist" "$rootfs" || return 1 | |
return 0 | |
} | |
install_debian() | |
{ | |
cache="/var/cache/lxc/debian" | |
mkdir -p /var/lock/subsys/ | |
( | |
flock -n -x 200 | |
if [ $? -ne 0 ]; then | |
echo "Cache repository is busy." | |
return 1 | |
fi | |
echo "Checking cache download in $cache/rootfs-$dist ... " | |
if [ ! -e "$cache/rootfs-$dist" ]; then | |
download_debian | |
if [ $? -ne 0 ]; then | |
echo "Failed to download 'debian base'" | |
return 1 | |
fi | |
fi | |
copy_debian | |
if [ $? -ne 0 ]; then | |
echo "Failed to copy rootfs" | |
return 1 | |
fi | |
return 0 | |
) 200>/var/lock/subsys/lxc | |
return $? | |
} | |
copy_configuration() | |
{ | |
cat <<EOF > "$rootfs/etc/hosts" | |
# The following lines are desirable for IPv6 capable hosts | |
::1 ip6-localhost ip6-loopback | |
fe00::0 ip6-localnet | |
ff00::0 ip6-mcastprefix | |
ff02::1 ip6-allnodes | |
ff02::2 ip6-allrouters | |
ff02::3 ip6-allhosts | |
127.0.0.1 localhost.localdomain localhost | |
# Auto-generated hostname. Please do not remove this comment. | |
10.0.0.$num $name | |
EOF | |
cat <<EOF > "$rootfs/etc/inittab" | |
# /etc/inittab: init(8) configuration. | |
# $Id: inittab,v 1.91 2002/01/25 13:35:21 miquels Exp $ | |
# The default runlevel. | |
id:2:initdefault: | |
# Boot-time system configuration/initialization script. | |
# This is run first except when booting in emergency (-b) mode. | |
si::sysinit:/etc/init.d/rcS | |
# What to do in single-user mode. | |
~:S:wait:/sbin/sulogin | |
# /etc/init.d executes the S and K scripts upon change | |
# of runlevel. | |
# | |
# Runlevel 0 is halt. | |
# Runlevel 1 is single-user. | |
# Runlevels 2-5 are multi-user. | |
# Runlevel 6 is reboot. | |
l0:0:wait:/etc/init.d/rc 0 | |
l1:1:wait:/etc/init.d/rc 1 | |
l2:2:wait:/etc/init.d/rc 2 | |
l3:3:wait:/etc/init.d/rc 3 | |
l4:4:wait:/etc/init.d/rc 4 | |
l5:5:wait:/etc/init.d/rc 5 | |
l6:6:wait:/etc/init.d/rc 6 | |
# Normally not reached, but fallthrough in case of emergency. | |
z6:6:respawn:/sbin/sulogin | |
# What to do when CTRL-ALT-DEL is pressed. | |
ca:12345:ctrlaltdel:/sbin/shutdown -t1 -a -r now | |
# The "id" field MUST be the same as the last | |
# characters of the device (after "tty"). | |
# | |
# Format: | |
# <id>:<runlevels>:<action>:<process> | |
# | |
# Note that on most Debian systems tty7 is used by the X Window System, | |
# so if you want to add more getty's go ahead but skip tty7 if you run X. | |
# | |
1:2345:respawn:/sbin/getty 38400 tty1 | |
2:23:respawn:/sbin/getty 38400 tty2 | |
3:23:respawn:/sbin/getty 38400 tty3 | |
4:23:respawn:/sbin/getty 38400 tty4 | |
EOF | |
cat <<EOF > "$path/$name/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 | |
# mounts point | |
lxc.mount.entry=proc $rootfs/proc proc nodev,noexec,nosuid 0 0 | |
lxc.mount.entry=devpts $rootfs/dev/pts devpts defaults 0 0 | |
lxc.mount.entry=sysfs $rootfs/sys sysfs defaults 0 0 | |
# network | |
lxc.network.type = veth | |
lxc.network.flags = up | |
lxc.network.link = br0 | |
lxc.network.veth.pair = veth_$name | |
# tun/tap | |
lxc.cgroup.devices.allow = c 10:200 rwm | |
EOF | |
if [ $? -ne 0 ]; then | |
echo "Failed to add configuration" | |
return 1 | |
fi | |
return 0 | |
} | |
clean() | |
{ | |
cache="/var/cache/lxc/debian" | |
if [ ! -e $cache ]; then | |
exit 0 | |
fi | |
# lock, so we won't purge while someone is creating a repository | |
( | |
flock -n -x 200 | |
if [ $? != 0 ]; then | |
echo "Cache repository is busy." | |
exit 1 | |
fi | |
echo -n "Purging the download cache..." | |
rm --preserve-root --one-file-system -rf "$cache" && echo "Done." || exit 1 | |
exit 0 | |
) 200>/var/lock/subsys/lxc | |
} | |
usage() | |
{ | |
cat <<EOF | |
Usage: $1 dist container-name container-number | |
EOF | |
return 0 | |
} | |
if [ $# -ne 3 ]; then | |
usage $(basename $0) | |
exit 1 | |
fi | |
dist="$1" | |
name="$2" | |
num="$3" | |
type debootstrap | |
if [ $? -ne 0 ]; then | |
echo "'debootstrap' command is missing" | |
exit 1 | |
fi | |
if [ "$(id -u)" != "0" ]; then | |
echo "This script should be run as 'root'" | |
exit 1 | |
fi | |
rootfs="$path/$name/rootfs" | |
install_debian | |
if [ $? -ne 0 ]; then | |
echo "failed to install debian" | |
exit 1 | |
fi | |
configure_debian | |
if [ $? -ne 0 ]; then | |
echo "failed to configure debian for a container" | |
exit 1 | |
fi | |
copy_configuration | |
if [ $? -ne 0 ]; then | |
echo "failed write configuration file" | |
exit 1 | |
fi |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment