Контейнеры LXC позволяют изолировать процессы и ресурсы, работающие в рамках
одной операционной системы, не прибегая к использованию виртуализации.
Положительным аспектом LXC является использование единого пространства
системных буферов, например, единый для базовой системы и всех контейнеров
дисковый кэш. Наиболее близкими аналогами LXC являются Solaris Zones и FreeBSD jail.
В качестве серверной операционной системы была использована Ubuntu 10.04 LTS, в
качестве виртуальных машин использован Debian Lenny.
Организация сетевого соединения для контейнера.
Воспользуемся сетевым мостом для создания общего сегмента сети.
Устанавливаем пакеты для создания моста:
sudo aptitude install bridge-utils
Настроим мост, для этого приведем файл /etc/network/interfaces к следующему виду:
# The loopback network interface
auto lo
iface lo inet loopback
# Комментируем активные до настройки сетевого моста опции
#allow-hotplug eth0
#iface eth0 inet dhcp
# Setup bridge
auto br0
iface br0 inet dhcp
bridge_ports eth0
bridge_fd 0
Как можно увидеть из файла /etc/network/interfaces, eth0 закомментирован и
добавлен новый интерфейс br0.
Далее перезапускаем сеть:
sudo /etc/init.d/networking restart
Если использует ручная настройка сети, то нужно сделать так:
auto br0
iface br0 inet static
bridge_ports eth0
bridge_fd 0
address 192.168.82.25
netmask 255.255.255.0
gateway 192.168.82.1
dns-nameservers 192.168.82.1
Установка LXC, установка cgroups
Установим lxc:
sudo aptitude install lxc
Создадим директорию /cgroup и примонтируем cgroup (может быть где угодно):
sudo mkdir /cgroup
Добавляем следующие строки в /etc/fstab:
cgroup /cgroup cgroup defaults 0 0
И монтируем cgroups:
sudo mount cgroup
До того как начать собирать контейнер, проверим окружение через lxc-checkconfig:
lxc-checkconfig
Kernel config /proc/config.gz not found, looking in other places...
Found kernel config file /boot/config-2.6.32-3-686
--- Namespaces ---
Namespaces: enabled
Utsname namespace: enabled
...
Все параметры должны быть включены (для ubuntu 10.04, в Debian squeeze Cgroup
memory controller: disabled ).
Создание первого контейнера
Мы будем использовать оригинальную версию скрипта lxc-debian, он находится в
файле /usr/share/doc/lxc/examples/lxc-debian.gz.
Скопируем файл /usr/share/doc/lxc/examples/lxc-debian.gz в /usr/local/sbin/
распакуем его и поставим бит запуска:
sudo cp /usr/share/doc/lxc/examples/lxc-debian.gz /usr/local/sbin/
sudo gunzip /usr/local/sbin/lxc-debian.gz
sudo chmod +x /usr/local/sbin/lxc-debian
Перед запуском этого скрипта требуется установить debootstrap.
sudo aptitude install debootstrap
Теперь сделаем первую вирутальную машину. По умолчанию директория развертывания
контейнеров находится в /var/lib/lxc/ , параметром -p можно указать
произвольное расположение вируальной машины.
sudo mkdir -p /lxc/vm0
sudo lxc-debian -p /lxc/vm0
Это может занять некоторое время. Скрипт так же настроит локаль. После
окончания установки нужно настроить виртуальную машину.
Идем в /lxc/vm0 и правим файл конфигурации (config):
lxc.tty = 4
lxc.pts = 1024
lxc.rootfs = /srv/lxc/vm0/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
# <<<< Добавляем эти строки
lxc.utsname = vm0
lxc.network.type = veth
lxc.network.flags = up
lxc.network.link = br0
# lxc.network.name = eth0
# lxc.network.hwaddr = 00:FF:12:34:56:78
lxc.network.ipv4 = 192.168.82.28/24
Рассмотрим параметры поподробнее:
lxc.utsname = vm0 Имя хоста виртуальной машины
lxc.network.type = veth Тип сети с которой работаем (man lxc.conf), используем
veth если работаем с мостом.
lxc.network.flags = up Сообщаем что нужно поднимать сетевой интерфейс при запуске системы.
lxc.network.link = br0 Мост через который будет работать вируальный интерфейс.
lxc.network.name = eth0 Имя сетевого интерфейса в контейнере. Если не
устанавливать будет eth0, по умолчанию.
lxc.network.hwaddr = 00:FF:12:34:56:78 Мак адрес устройства которое используется.
lxc.network.ipv4 = 192.168.82.28/24 Сетевой адрес который будет присвоен виртуальному интерфейсу.
Так же требуется отредактировать /etc/network/interfaces в контейнере (/lxc/vm0/rootfs/etc/network/interfaces)
Создаем контейнер который связывает имя конрейнера с файлом настроек. Имя будет
использовано для управления единичным контейнером.
sudo lxc-create -n vm0 -f /lxc/vm0/config
Запустим вируальную машину.
sudo lxc-start -n vm0 -d
Проверяем запущена ли она:
sudo lxc-info -n vm0
'vm0' is RUNNING
Теперь можно подключиться к консоли контейнера используя lxc-console:
sudo lxc-console -n vm0
Вводим имя пользователя root и получаем вход в систему (без пароля).
Устанавливаем пароль пользователю root:
sudo passwd
Добавляем не привилегированного пользователя.
sudo adduser admin
Хорошо наш контейнер работает, теперь остановим его делается это следующим образом:
sudo lxc-stop -n vm0
И проверяем его статус через lxc-info
sudo lxc-info -n vm0
'vm0' is STOPPED
Еще один контейнер
У нас есть контейнер vm0 с минимальной системой и установленными паролями рута
и не привилегированного пользователя, из этого контейнера клонируем еще один.
Для этого первая виртуальная машина должна быть остановлена. Создаем папку vm1
в /lxc и копируем туда содержимое vm0
cd /lxc
sudo mkdir vm1
sudo cp -Rv ./vm0/* ./vm1/
cd ./vm1/
Теперь нужно подправить файл конфигурации для vm1 (сеть, имя и т.д.)
Ограничения
При настройке Xen или KVM можно настроить количество памяти, количество
виртуальных процессов, а так же настроить планировщик. Это же можно сделать с
помощью cgroups в LXC. Прежде нужно запомнить что все настройки cgroup
полностью динамические, т.е. вы можете их изменять в любое время, так что
будьте осторожны.
Все значения cgroup можно задать следующими способами:
lxc-cgroup -n vm0 <cgroup-name> <value>
echo <value> > /cgroup/vm0/<cgroup-name>
в конфигурационном файле: "lxc.cgroup.<cgroup-name> = <value>"
В примерах будем использовать настройку через конфигурационный файл.
Для обозначения размера, например памяти, можно использовать K, M или G, например:
echo "400M" > /cgroup/vm0/memory.limit_in_bytes
Допустимые параметры. Для начала, мы можем посмотреть в каталог /cgroup/vm0
(если vm0 не запущен - запустите сейчас). Мы можем увидеть следующее:
ls -1 /cgroup/vm0/
cgroup.procs
cpuacct.stat
cpuacct.usage
cpuacct.usage_percpu
cpuset.cpu_exclusive
cpuset.cpus
cpuset.mem_exclusive
cpuset.mem_hardwall
cpuset.memory_migrate
cpuset.memory_pressure
cpuset.memory_spread_page
cpuset.memory_spread_slab
cpuset.mems
cpuset.sched_load_balance
cpuset.sched_relax_domain_level
cpu.shares
devices.allow
devices.deny
devices.list
freezer.state
memory.failcnt
memory.force_empty
memory.limit_in_bytes
memory.max_usage_in_bytes
memory.memsw.failcnt
memory.memsw.limit_in_bytes
memory.memsw.max_usage_in_bytes
memory.memsw.usage_in_bytes
memory.soft_limit_in_bytes
memory.stat
memory.swappiness
memory.usage_in_bytes
memory.use_hierarchy
net_cls.classid
notify_on_release
tasks
Не будем вдаваться в описание каждого параметра, подробно можно посмотреть здесь.
Ограничение памяти и файла подкачки
Не снижайте количество памяти для запущенного контейнера, если вы не уверены что делаете.
Максимальное количество памяти для виртуальной машины:
lxc.cgroup.memory.limit_in_bytes = 256M
Максимальное количество swap для виртуальной машины:
lxc.cgroup.memory.memsw.limit_in_bytes = 1G
Больше информации по работе с памятью можно найти здесь.
Ограничение CPU
Есть два варианта ограничения CPU. Первый, можно ограничить через планировщик и
второй - можно ограничить через cgroup.
Планировщик
Планировщик работает следующим образом: Можно присвоить vm0 значение 10 и vm1
значение 20. Это означает что каждую секунду процессорного времени vm1 получит
двойное количество циклов процессора. По умолчанию значение установлено в 1024.
lxc.cgroup.cpu.shares = 512
Больше о планировщике CPU читаем здесь.
Так же можно установить количество используемых процессоров в контейнере.
Допустим у вас 4 CPU, то по умолчанию для всех является значение 0-3
(использовать все процессоры).
Использовать первый cpu:
lxc.cgroup.cpuset.cpus = 0
использовать первый, второй и последний cpu.
lxc.cgroup.cpuset.cpus = 0-1,3
использовать первый и последний cpu.
lxc.cgroup.cpuset.cpus = 0,3
Подробнее здесь.
Ограничение жесткого диска
Пока это нельзя сделать через cgroups, но можно сделать через LVM.
Как безопасно остановить виртуальную машину
lxc-stop просто убивает родительский процесс lxc-start, если требуется
безопасно выключить, то в настоящие время не существует другого решения, как
остановить виртуальную машину через SSH или lxc-console:
sudo lxc-console -n vm0
#vm0> init 0
Нужно подождать пока остановятся все процессы (за этим можно понаблюдать через
pstree или htop) и затем останавливаем виртуальную машину.
sudo lxc-stop -n vm0
Как навсегда удалить виртуальную машину
Останавливаем виртуальную машину и используем команду lxc-destroy
sudo lxc-destroy -n vm0
Она удалит все файлы из /lxc/vm0, так сказано в документации, но она не удалила
файлы из каталога поэтому пришлось удалять самому.
Как заморозить и "разморозить" контейнер
LXC может заморозить все процессы в запущенном контейнере, тем самым LXC просто
блокирует все процессы.
sudo lxc-freeze -n vm0
После запуска все будет записано в память (и swap).
Использованные источники
* http://www.ibm.com/developerworks/ru/library/l-lxc-containers/
* https://help.ubuntu.com/community/LXC
* http://blog.bodhizazen.net/linux/lxc-configure-ubuntu-lucid-containers/
* http://blog.bodhizazen.net/linux/lxc-linux-containers/
* http://lxc.teegra.net/#_setup_of_the_controlling_host
* http://blog.foaa.de/2010/05/lxc-on-debian-squeeze/#pni-top0
|