Linux VServer

VServer

I used to use Linux VServers to have services run in their own Linux installation. This seemed to have only advantages for me:

  • Each VServer Linux installation has only the minimum amount of packages installed to offer their service. I use

debfoster and deborphan to preserve the current status.

  • The access to the ports of each VServer is restricted by a packet filter on the host.
  • If a a security hole in one of the services allows to break into the system the intruder only has access to the affected VServer and not to all the other VServers with their services. Additionally the rights of each VServer can be restricted CAPABILITIES).
  • It's no longer necessary to install many (any) public reachable services on the host-system so it's much harder to attack it.
  • The host-system can observe the VServers, for example with Integrit
  • The VServers run without having their own kernel. If the Verserver idls they hardly consume any resources. Additionally thanks to vhashify files that exist on several Verserver only use space on the hard disk once.
  • It's very easy to create new installations (e.g. for testing) and you can even give root access to friends without the risk that they accidently interfere important things.

VServer Installation

Get the VServer kernel-patch, apply it and boot the patched kernel. Install the VServer utils (I used the Debian VServer utils)

Now this is all you need to do to get a new VServer:

# find free context id
find /etc/vservers/ -name context -exec cat '{}' ';' | sort -n
# assume 1234 is still unused
vserver foo build -m debootstrap --hostname foo.example.com --netdev eth0 --interface 10.0.1.5/32 --context 1234 -- -d jessie

This will create a VServer called "foo" with a Debian jessie Installation, the VServer believes be named foo.example.com and will have the IP-address 10.0.1.5.

Create a Gentoo VServer:

vserver-new mygentoo --hostname mygentoo --interface eth0:10.0.1.6 --context 1253 stage3 ./stage3-i686-20060317.tar.bz2 x86

The stage file can be found on each Gentoo mirror, the vserver-new script can be found in the Gentooo vserver package. See also the Gentoo Linux-VServer howto.

In order to make it possible to use vhashify (yes, the folder is called vunify not vhashify):

mkdir -p /etc/vservers/foo/apps/vunify

Exclude the folder from the vhashify (for all vservers):

/usr/lib/util-vserver/defaults/vunify-exclude

VServer File Permissions

If you can't delete a file:

# whoami
# ls -ld foo/bar.txt
# ls -ld foo/
# lsattr foo/bar.txt
# lsattr -d foo/
# showattr foo/bar.txt
# showattr foo/

(in the showattr output only upper case letters are really active)

# su
# chmod u+w foo/
# chmod u+w foo/bar.txt
# chattr -i foo/bar.txt
# setattr --~iunlink-but-not-immutable foo/bar.txt
# setattr --~iunlink-but-not-immutable foo

VServer Configuration

  • In order to allow the VServer to raise the priority of a process (cron-jobs which start su with a nice level will need this):
/etc/vservers/foo/flags
igneg_nice
  • Automatically start a VServer while booting:
/etc/vservers/foo/apps/init/mark
default

If you have lots of VServers or if some of your vservers have to be started in a given order, you can use other names instead of "default". Don't forger to copy and modify the "default" init.d vserver script to also start and stop (at the desired time) the other VServers.

VServer Masquerading SNAT

My VServers all have private IP-addresses. The following iptables instruction (issued on the host-system) will rewrite all packages from to vserver to look like they came the public IP of the host. (fill/replace the variables with your values):

iptables -t nat -I POSTROUTING -s $VSERVER_NET ! -d $VSERVER_NET -j SNAT --to $EXT_IP

xinetd

If there are services (like e.g. ssh) which should run on the host and on the VServers you need to prevent the host system to acquire all request for your service. Therefore bind the service on the host only to some (one) ip address and not to all. Most services that are started as deamon can be configured this way, services started via inetd must be switched to xinetd. In xinetd it's quite easy:

bind = 10.0.0.1