Last week I introduced you to LXC, or Linux Resource Containers. We looked at the requirements to get LXC up and running and looked at isolating individual processes using application containers. In this tip, we go one step further, from isolating a single application to creating a fully separate container that runs a full service or set of services. This tip assumes that LXC has been previously configured, as discussed last week.
The easiest way to set up an LXC-based container is to use an existing base operating system, such as the templates provided by the OpenVZ project. As an example, we'll use a CentOS 5 template: centos-5-x86.tar.gz. Once you download it, the LXC system container can be created. LXC also provides two tools to assist in creating Fedora or Debian containers: lxc-fedora and lxc-debian. Each of these will download a minimal install and interactively set up the container; pass the "install" option to either script to use them to install a new container.
To use an OpenVZ container, use:
# mkdir -p /srv/lxc/centos5
# cd /srv/lxc/centos5
# tar xvzf ~/centos-5-x86.tar.gz
This unpacks the base template into /srv/lxc/centos5 which is where the container will live. The next step is to create an LXC configuration file, for example /etc/lxc/lxc-centos.conf:
lxc.utsname = centos
lxc.network.type = veth
lxc.network.flags = up
lxc.network.link = br0
lxc.network.name = eth0
lxc.network.hwaddr = 4a:49:43:49:79:bd
# use 0.0.0.0 below for DHCP
lxc.network.ipv4 = 192.168.250.150
lxc.mount = /etc/lxc/lxc-centos.fstab
lxc.rootfs = /srv/lxc/centos5
Next, create the fstab file for the container as noted above by the lxc.mount option, /etc/lxc/lxc-centos.fstab:
none /srv/lxc/centos5/dev/pts devpts defaults 0 0
none /srv/lxc/centos5/proc proc defaults 0 0
none /srv/lxc/centos5/sys sysfs defaults 0 0
Finally, it is time to initialize the container for use:
# lxc-create -f /etc/lxc/lxc-centos.conf -n centos
If you need to destroy the container, you can do so using lxc-destroy -n centos; this does not destroy the actual filesystem for the container or the configuration files, just the system container object. If you make a mistake in the configuration, using lxc-destroy and then lxc-create is fast and easy.
For the CentOS example, the network settings inside the container must be changed. Since this is an OpenVZ template, it may be looking for the venet0 device, which is not provided (in the configuration, we've set it to eth0), or the configuration for networking may not be there at all. Regardless, the file /srv/lxc/centos5/etc/sysconfig/network-scripts/ifcfg-eth0 must be created, and should contain:
The above example is for a static IP address setup; DHCP could be used as well with the appropriate changes to the LXC configuration file.
Finally, you need to add a user to the container so that you can login via SSH. Because it is essentially a full filesystem, you can "enter" the container by using chroot:
# chroot /srv/lxc/centos5
# useradd user
# passwd user
While still in the chroot, you can also determine what services should be started and which should not. You will also want to fix the /etc/mtab file. By default, it will start in runlevel 3, so (still in the chroot), execute:
# chkconfig --list|grep '3:on'
# chkconfig httpd off
# chkconfig saslauthd off
# rm /etc/mtab
# touch /etc/mtab
Turn off, or on, any services you want. Ensure that the sshd service is set to start because, other than via chroot, that will be the only entrance to the container.
Now that the container is set up, it can be started. On the first run you may want to run it straight-out, but since it will grab and hang onto the controlling terminal, starting it under screen is best. The command below will start it, detached, in screen:
# screen -dmS lxc-centos lxc-start -n centos
This will start the system as if it were a virtual machine, by starting init within the container. If you start it under screen, you can attach to the screen session to watch it "boot" by using screen -x lxc-centos. And to stop the container:
# lxc-stop -n centos
There is obviously much more to LXC than this, and plenty of configuration that can be done in the container once it is set up. This will get you to the state where you can do that, and enjoy playing around with what is essentially a full-fledged virtual machine, without the overhead of virtualization. It lacks the polish that OpenVZ has, but that will come in time, and the fact that it is part of the Linux kernel and can sandbox individual applications, are benefits that even OpenVZ does not provide.
Get the PDF version of this post here.
Vincent Danen works on the Red Hat Security Response Team and lives in Canada. He has been writing about and developing on Linux for over 10 years and is a veteran Mac user.