Установка Calculate LXC Desktop

lxc-desktop

Предупреждение

Поддержка проекта прекращена

Введение

LXC-desktop позволяет запускать полноценную систему с графическим интерфейсом в изолированном окружении. В качестве хост-системы, на которой выполняется запуск контейнеров, мы подготовили дистрибутив Calculate Linux Container (CLC). Для установки в контейнере можно использовать Calculate Container Desktop Xfce (CCDX). В то время как CLC не имеет графического интерфейса и состав пакетов в нём сведён к минимуму, CCDX, напротив, является почти полной копией Calculate Linux Desktop Xfce - за исключением ядра, загрузчика и некоторых системных утилит.

Используя lxc-desktop, вы получаете все плюсы от работы с контейнерами - изоляцию систем, минимальные системные требования при запуске нескольких контейнеров, возможность быстрой установки, настройки, загрузки и т.д. Системы, запущенные в контейнере, никак не связаны с хост-системой. Вы можете связать их с одним или несколькими мониторами (при использовании нескольких видеокарт), при этом используя аппаратные возможности каждой видеокарты.

Настройка хост-системы

В качестве хост-системы для работы контейнера используется дистрибутив Calculate Linux Container. При использовании другого дистрибутива вам потребуется установить пакет app-emulation/lxc.

Установите систему на жесткий диск и выполните описанные ниже настройки.

Настройка сети

Для доступа к сети контейнеров создайте сетевой мост из интерфейса eth0. Для этого выполните следующие настройки:

/etc/conf.d/net

modules="!plug"
ifplugd="--no-beep"
config_eth0="null"
bridge_br0="eth0"
config_br0="dhcp"
bridge_stp_state_br0=0
bridge_hello_time_br0=1000
bridge_forward_delay_br0=0

Перезапустите сеть:

/etc/init.d/net.eth0 stop

rm /etc/init.d/net.et*

ln -sf /etc/init.d/net.lo /etc/init.d/net.br0

/etc/init.d/net.br0 start

Установка lxc-desktop

Установим систему Calculate Container Desktop Xfce в контейнер. Для установки выполните команду:

lxc-create -t download -n pc100 -- --server mirror.calculate-linux.org --no-validate -d CCDX --arch x86_64

(потребуется ввести номер версии дистрибутива),

где pc100 - имя контейнера, участвующее в дальнейших настройках и используемое в качестве сетевого имени.

Настройка контейнера

Добавьте настройки сети для контейнера и права на запись в /sys, дописав в конец файла:

/var/calculate/lxc/pc100/config

# Network configuration
lxc.net.0.type = veth
lxc.net.0.flags = up
lxc.net.0.name = eth0
lxc.net.0.link = br0
lxc.net.0.hwaddr = 02:03:04:05:06:07

lxc.mount.auto = cgroup:mixed proc:mixed sys:rw
lxc.environment = LXC_DESKTOP=1

Измените MAC-адрес 02:03:04:05:06:07 на любой другой. Обратите внимание, что первое число должно быть чётным.

Настройки системы в контейнере

Запустите контейнер:

lxc-start -n pc100

После запуска откроется графическое приглашение к вводу пароля. Во время первой загрузки будет создан пользователь guest с паролем "guest". Вернитесь в консоль при помощи комбинации клавиш Ctrl+Alt+F1.

Выполните базовые настройки: пароль root, запуск демона ssh, локализация системы. Теперь перезапустите контейнер:

lxc-attach -n pc100 passwd

lxc-attach -n pc100 -- cl-setup-locale -l ru_RU --timezone Europe/Moscow

lxc-stop -r -n pc100

Используйте свои значения локализации ru_RU и временной зоны Europe/Moscow.

Добавление контейнера в автозагрузку

Добавьте контейнер в автозагрузку системы:

ln -sf /etc/init.d/lxc /etc/init.d/lxc.pc100

rc-update add lxc.pc100

Для того, чтобы система в контейнере стартовала после поднятия сети, создайте файл:

/etc/conf.d/lxc

rc_want="net.br0"

Настройка нескольких контейнеров с одним рабочим местом

Настройка хост-системы

Создайте файл с правилами udev для разделения устройств вывода, отдав tty7 контейнеру pc100, а tty8 контейнеру pc101:

/etc/udev/rules.d/95-id-lxc.rules

ACTION=="add|remove", KERNEL=="tty7", ENV{ID_LXC}="pc100"
ACTION=="add|remove", KERNEL=="tty8", ENV{ID_LXC}="pc101"

Важно

Номер 95 в имени файла не следует менять.

Перечитайте правила udev для принятия изменений:

/etc/init.d/udev reload

Настройка первого контейнера

Отредактируйте настройки системы первого контейнера:

/var/calculate/lxc/pc100/rootfs/etc/calculate/ini.env

[xorg]
vt = 7

Выполните обновление настроек системы в контейнере:

lxc-attach -n pc100 cl-setup-system

Установка второго контейнера

Установите второй контейнер:

lxc-create -t download -n pc101 -- --server mirror.calculate-linux.org --no-validate -d CCDX --arch x86_64

(потребуется ввести номер версии дистрибутива),

где pc101 - имя контейнера, участвующее в дальнейших настройках и используемое в качестве сетевого имени.

Настройка второго контейнера

Добавьте настройки сети для контейнера и права на запись в /sys, дописав в конец файла:

/var/calculate/lxc/pc101/config

# Network configuration
lxc.net.0.type = veth
lxc.net.0.flags = up
lxc.net.0.name = eth0
lxc.net.0.link = br0
lxc.net.0.hwaddr = 04:05:06:07:08:09

lxc.mount.auto = cgroup:mixed proc:mixed sys:rw
lxc.environment = LXC_DESKTOP=1

Измените MAC)адрес 04:05:06:07:08:09 на любой другой. Не забывайте, что первое число должно быть чётным.

Настройте второй контейнер по аналогии с первым, указав для него восьмой терминал:

/var/calculate/lxc/pc101/rootfs/etc/calculate/ini.env

[xorg]
vt = 8

Запустите второй контейнер и выполните базовые настройки: пароль root, запуск демона ssh, локализация системы, обновление всех настроек:

lxc-start -n pc101

lxc-attach -n pc101 passwd

lxc-attach -n pc101 -- cl-setup-locale -l ru_RU --timezone Europe/Moscow

Используйте свои значения локализации ru_RU и временной зоны Europe/Moscow.

Добавьте второй контейнер в автозагрузку системы:

ln -sf /etc/init.d/lxc /etc/init.d/lxc.pc101

rc-update add lxc.pc101

Перезагрузите оба контейнера:

lxc-stop -r -n pc100

lxc-stop -r -n pc101

Для переключения между графическими сеансами двух работающих lxc-desktop используйте комбинации клавиш Ctrl+Alt+F7 и Ctrl+Alt+F8.

Настройка нескольких контейнеров с несколькими рабочими местами

lxc-desktop с несколькими рабочими местами

Для запуска такой конфигурации понадобится системный блок с несколькими видеокартами.

Распределение USB-устройств

Распределить устройства между двумя рабочими местами можно двумя способами: через разделение USB-портов на материнской плате либо назначив отдельные устройства USB hub для каждого рабочего места.

Рассмотрите вариант разделения USB-портов на материнской плате, запустив монитор подключенных устройств и начав подключать устройства поочерёдно во все USB-порты. На выходе получим лог, по которому необходимо будет сопоставить системный путь устройства и USB-порт:

udevadm monitor -u -s usb/usb_device
UDEV  [5101.730402] add      /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5101.775152] bind     /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5101.775593] change   /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5101.780696] change   /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5103.337561] unbind   /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5103.337581] remove   /devices/pci0000:00/0000:00:14.0/usb1/1-2 (usb)
UDEV  [5106.507789] add      /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5106.552851] bind     /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5106.552960] change   /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5106.559699] change   /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5107.587480] unbind   /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5107.587513] remove   /devices/pci0000:00/0000:00:14.0/usb1/1-1 (usb)
UDEV  [5109.653942] add      /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
UDEV  [5109.714358] bind     /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
UDEV  [5109.714593] change   /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
UDEV  [5109.720462] change   /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
UDEV  [5110.624758] unbind   /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
UDEV  [5110.624792] remove   /devices/pci0000:00/0000:00:14.0/usb1/1-10 (usb)
...

Сложность сопоставления системного пути устройства и порта USB заключается в том, что USB-порты с поддержкой USB3 идентифицируются по-разному, если к ним подключить USB3-устройство (например, флешку) или USB1 / USB2 (например, мышь). Это видно и по приведённому выше логу (вначале была подключена мышь, а затем USB HDD). В итоге получаем соответствия:

порт тип USB устройство
PORT1 USB 1-3 /devices/pci0000:00/0000:00:14.0/usb1/1-9
PORT2 USB 1-3 /devices/pci0000:00/0000:00:14.0/usb1/1-10
PORT3 USB 2-3 /devices/pci0000:00/0000:00:14.0/usb2/1-2
PORT3 USB 1 /devices/pci0000:00/0000:00:14.0/usb2/2-2
PORT4 USB 2-3 /devices/pci0000:00/0000:00:14.0/usb1/1-1
PORT4 USB 1 /devices/pci0000:00/0000:00:14.0/usb2/2-1
PORT5 USB 1-3 /devices/pci0000:00/0000:00:14.0/usb1/1-12
PORT6 USB 1-3 /devices/pci0000:00/0000:00:14.0/usb1/1-11

Отдайте порты 1-3 рабочему месту pc100, а порты 4-6 порты - pc101, добавив правила:

/etc/udev/rules.d/95-id-lxc.rules

# USB devices
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-9/*", ENV{ID_LXC}="pc100"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-10/*", ENV{ID_LXC}="pc100"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-2/*", ENV{ID_LXC}="pc100"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb2/2-2/*", ENV{ID_LXC}="pc100"

ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-1/*", ENV{ID_LXC}="pc101"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb2/2-1/*", ENV{ID_LXC}="pc101"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-12/*", ENV{ID_LXC}="pc101"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:14.0/usb1/1-11/*", ENV{ID_LXC}="pc101"

При использовании USB-хабов задача сильно упрощается, так как в этом случае достаточно определить и добавить один порт, в который включено устройство. Все устройства, подключенные к хабу, будут располагаться внутри пути.

Распределение видеокарт

Если используются видеоустройства разных производителей - например, встроенная карта Intel и внешняя ATI, то необходимо добавить в автозагрузку модуль radeon. Для этого добавьте запись:

/etc/modules-load.d/lxc-desktop.conf

radeon

При этом удалите модуль radeon из списка незагружаемых модулей:

/etc/modprobe.d/blacklist-calculate.conf

# hplip and cups 1.4+ use raw USB devices, so it requires usblp not be loaded
blacklist usblp

# You probably want this to not get the console beep loud on every tab :)
blacklist pcspkr

# Not using kernel video drivers
blacklist amdgpu
blacklist nouveau
blacklist nvidia
#blacklist radeon
blacklist uvesafb
blacklist vboxvideo

Перезапустите modules-load:

/etc/init.d/modules-load restart

Получите системные пути видеокарт, выполнив:

udevadm trigger -c add -nv -s drm | awk -F/drm/ '{print $1}' | uniq

/sys/devices/pci0000:00/0000:00:01.0/0000:01:00.0
/sys/devices/pci0000:00/0000:00:02.0

Теперь вы можете получить информацию о видеокарте, выполнив:

udevadm info /sys/devices/pci0000:00/0000:00:01.0/0000:01:00.0

Отдайте ATI контейнеру pc100, а Intel - контейнеру pc101, добавив запись:

# Video
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:01.0/0000:01:00.0/*", ENV{ID_LXC}="pc100"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:02.0/*", ENV{ID_LXC}="pc101"

Устройства терминалов

Чтобы Xorg-сервер контейнера pc100 располагался на tty7, а контейнера pc101 на tty8, добавим правила:

/etc/udev/rules.d/95-id-lxc.rules

ACTION=="add|remove", KERNEL=="tty7", ENV{ID_LXC}="pc100"
ACTION=="add|remove", KERNEL=="tty8", ENV{ID_LXC}="pc101"

Звук

Если звуковая карта одна, то подсистему звука можно целиком отдать в один контейнер. Если же звуковых карт две, то следует получить список путей до устройств:

udevadm trigger -c add -nv -s sound

после чего добавить правила в udev. Также не забудьте пробросить устройство /sys/devices/virtual/sound/timer во все контейнеры, в которых будет звук.

Пример проброса всего звука в один контейнер:

/etc/udev/rules.d/95-id-lxc.rules

ACTION=="add|remove", SUBSYSTEM=="sound", ENV{ID_LXC}="pc100"

Пример проброса разных звуковых карт в различные контейнеры:

/etc/udev/rules.d/95-id-lxc.rules

# audio (udevadm trigger -c add -nv -s sound)
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:1f.3/*", ENV{ID_LXC}="pc100"
ACTION=="add|remove", DEVPATH=="/devices/pci0000:00/0000:00:1f.4/*", ENV{ID_LXC}="pc101"
ACTION=="add|remove", DEVPATH=="/devices/virtual/sound/timer", ENV{ID_LXC}="pc100 pc101"

PS/2

Пробросим PS/2 порт в контейнер pc101, добавив правила:

/etc/udev/rules.d/95-id-lxc.rules

# PS/2
ACTION=="add|remove", DEVPATH=="/devices/platform/i8042/*", ENV{ID_LXC}="pc101"

Настройка контейнеров

Запустите первый контейнер и выполните настройки системы:

lxc-start -n pc100

/var/calculate/lxc/pc100/rootfs/etc/calculate/ini.env

[xorg]
busid = PCI:1:0:0
sharevts = on
vt = 7

Параметр busid можно получить при помощи утилиты lspci:

00:02.0 -> PCI:0:2:0
01:00.0 -> PCI:1:0:0

Выполните настройку видео и общие настройки системы первого контейнера:

lxc-attach -n pc100 -- cl-setup-video --video radeon

lxc-attach -n pc100 cl-setup-system

Запустите и настройте второй контейнер по аналогии с первым, указав восьмой терминал:

lxc-start -n pc101

/var/calculate/lxc/pc101/rootfs/etc/calculate/ini.env

[xorg]
busid = PCI:0:2:0
sharevts = on
vt = 8

Выполните настройку видео и общие настройки системы второго контейнера:

lxc-attach -n pc101 -- cl-setup-video --video intel

lxc-attach -n pc101 cl-setup-system

Перезапустите оба контейнера:

lxc-stop -r -n pc100

lxc-stop -r -n pc101