мета-данные страницы
Различия
Показаны различия между двумя версиями страницы.
| Предыдущая версия справа и слеваПредыдущая версияСледующая версия | Предыдущая версия | ||
| notes:howlinuxworks:vol6 [2026/05/14 15:13] – radi0dev | notes:howlinuxworks:vol6 [2026/05/14 16:59] (текущий) – radi0dev | ||
|---|---|---|---|
| Строка 160: | Строка 160: | ||
| Полный список см. systemd.unit(5) | Полный список см. systemd.unit(5) | ||
| - | ===== 6.3.4. Процесс работы systemd ===== | + | ===== 6.3.4 Процесс работы systemd ===== |
| systemctl - основная команда для управления systemd юнитами. | systemctl - основная команда для управления systemd юнитами. | ||
| Строка 221: | Строка 221: | ||
| **Примечание: | **Примечание: | ||
| + | ==== 6.3.5 Отслеживание и синхронизация процессов systemd ==== | ||
| + | |||
| + | systemd использует **cgroups** (группы управления ядра Linux) для отслеживания иерархии процессов. Параметр **Type** в юнит-файле указывает поведение службы при запуске. | ||
| + | |||
| + | ^ Type ^ Описание ^ | ||
| + | | **simple** | Процесс не разветвляется, | ||
| + | | **forking** | Процесс разветвляется; | ||
| + | | **notify** | Служба отправляет уведомление systemd, когда готова | | ||
| + | | **dbus** | Служба регистрируется на D-Bus, когда готова | | ||
| + | | **oneshot** | Процесс полностью завершается после запуска; | ||
| + | | **idle** | Как simple, но запуск отложен до завершения всех активных заданий | | ||
| + | |||
| + | **Примечание: | ||
| + | |||
| + | ==== 6.3.6 Зависимости systemd ==== | ||
| + | |||
| + | Гибкая система зависимостей требует баланса между строгостью и отказоустойчивостью. Слишком строгие правила могут заблокировать доступ при сбое некритичного сервиса. systemd предлагает несколько типов зависимостей для гибкого управления: | ||
| + | |||
| + | ^ Тип ^ Описание ^ | ||
| + | | **Requires** | Строгие зависимости. При сбое зависимости юнит также отключается. | | ||
| + | | **Wants** | Зависимости только для активации. Сбой зависимости не влияет на юнит. Рекомендуется использовать по возможности. | | ||
| + | | **Requisite** | Юниты, которые уже должны быть активны. Если не активны, | ||
| + | | **Conflicts** | Отрицательные зависимости. При активации юнита противоположная зависимость деактивируется. | | ||
| + | |||
| + | Просмотр зависимостей: | ||
| + | <code bash> | ||
| + | systemctl show -p type unit | ||
| + | </ | ||
| + | |||
| + | === Порядок выполнения юнитов === | ||
| + | |||
| + | По умолчанию юниты с Requires и Wants запускаются одновременно. Для упорядочивания используйте: | ||
| + | |||
| + | * **Before** - текущий юнит активируется раньше перечисленных | ||
| + | * **After** - текущий юнит активируется после перечисленных | ||
| + | |||
| + | systemd ждет активного статуса юнита перед активацией зависимостей. | ||
| + | |||
| + | === Зависимости по умолчанию === | ||
| + | |||
| + | systemd автоматически добавляет зависимость After к Wants-зависимостям. Эти неявные зависимости вычисляются во время загрузки и не сохраняются в файлах конфигурации. | ||
| + | |||
| + | Отключить зависимости по умолчанию: | ||
| + | <code bash> | ||
| + | DefaultDependencies=no | ||
| + | </ | ||
| + | |||
| + | === Условные зависимости === | ||
| + | |||
| + | Для проверки состояния системы: | ||
| + | |||
| + | * **ConditionPathExists=p** - путь существует | ||
| + | * **ConditionPathIsDirectory=p** - путь является каталогом | ||
| + | * **ConditionFileNotEmpty=p** - файл существует и не пуст | ||
| + | |||
| + | При ложном условии юнит не активируется, | ||
| + | |||
| + | === Секция [Install] и включение юнитов === | ||
| + | |||
| + | Раздел [Install] позволяет указывать зависимости в обратном порядке без изменения дополнительных файлов. Используйте **WantedBy** или **RequiredBy**. | ||
| + | |||
| + | Пример: | ||
| + | |||
| + | **test1.target: | ||
| + | <code bash> | ||
| + | [Unit] | ||
| + | Description=test 1 | ||
| + | |||
| + | [Install] | ||
| + | WantedBy=test2.target | ||
| + | </ | ||
| + | |||
| + | **test2.target: | ||
| + | <code bash> | ||
| + | [Unit] | ||
| + | Description=test 2 | ||
| + | </ | ||
| + | |||
| + | Включение юнита: | ||
| + | <code bash> | ||
| + | systemctl enable test1.target | ||
| + | # Создаст: | ||
| + | </ | ||
| + | |||
| + | Отключение юнита: | ||
| + | <code bash> | ||
| + | systemctl disable test1.target | ||
| + | </ | ||
| + | |||
| + | **Важно: | ||
| + | |||
| + | Каталоги .wants и .require в / | ||
| + | |||
| + | ==== 6.3.7 Запуск по запросу и параллелизация ресурсов в systemd ==== | ||
| + | |||
| + | systemd позволяет откладывать запуск юнита до момента, | ||
| + | |||
| + | 1. Создается юнит systemd для сервиса (Unit A) | ||
| + | 2. Определяется ресурс (сокет, | ||
| + | 3. Создается юнит ресурса (Unit R): .socket, .path или .device | ||
| + | 4. systemd мониторит ресурс и активирует Unit A при обращении | ||
| + | |||
| + | При обращении к ресурсу: | ||
| + | 1. systemd блокирует ресурс и буферизует входные данные | ||
| + | 2. Активирует Unit A | ||
| + | 3. Unit A берет управление ресурсом и обрабатывает буферизованные данные | ||
| + | |||
| + | **Важные замечания: | ||
| + | * Юнит ресурсов должен охватывать все точки доступа сервиса | ||
| + | * Связь между юнитами может быть неявной (по имени) или явной (параметр Socket=) | ||
| + | * Не все серверы поддерживают взаимодействие с юнитами ресурсов | ||
| + | |||
| + | === Пример: | ||
| + | |||
| + | Echo-сервис на TCP-порту 22222. | ||
| + | |||
| + | **echo.socket: | ||
| + | <code bash> | ||
| + | [Unit] | ||
| + | Description=echo socket | ||
| + | |||
| + | [Socket] | ||
| + | ListenStream=22222 | ||
| + | Accept=true | ||
| + | </ | ||
| + | |||
| + | **echo@.service: | ||
| + | <code bash> | ||
| + | [Unit] | ||
| + | Description=echo service | ||
| + | |||
| + | [Service] | ||
| + | ExecStart=/ | ||
| + | StandardInput=socket | ||
| + | </ | ||
| + | |||
| + | Запуск: | ||
| + | <code bash> | ||
| + | systemctl start echo.socket | ||
| + | telnet localhost 22222 | ||
| + | </ | ||
| + | |||
| + | Остановка: | ||
| + | <code bash> | ||
| + | systemctl stop echo.socket | ||
| + | </ | ||
| + | |||
| + | === Экземпляры и передача управления === | ||
| + | |||
| + | Символ @ в имени echo@.service означает параллельные экземпляры. При **Accept=true** в сокет-юните systemd принимает входящие соединения и создает отдельный экземпляр для каждого. Каждый экземпляр считывает данные как стандартный ввод. | ||
| + | |||
| + | Если сервис может самостоятельно принимать соединения, | ||
| + | |||
| + | Документация: | ||
| + | |||
| + | === Оптимизация загрузки с помощью юнитов ресурсов === | ||
| + | |||
| + | Юниты ресурсов ускоряют загрузку путем параллельной активации: | ||
| + | |||
| + | ^ Последовательный запуск ^ Параллельный запуск с юнитом ресурса ^ | ||
| + | | Служба E (ресурс R) запускается | Юнит R активируется немедленно | | ||
| + | | Службы A, B, C ждут E | Службы A, B, C, E стартуют параллельно | | ||
| + | | Долгое время загрузки | Быстрая загрузка, | ||
| + | |||
| + | systemd предоставляет интерфейс юнита ресурса (R) еще до полной активации служебного юнита (E). Это позволяет зависимым юнитам (A, B, C) стартовать параллельно, | ||
| + | |||
| + | **Побочный эффект: | ||
| + | |||
| + | **Пример: | ||
| + | |||
| + | ==== 6.3.8 Вспомогательные компоненты systemd ==== | ||
| + | |||
| + | systemd включает поддержку задач управления системой, | ||
| + | |||
| + | ^ Служба ^ Назначение ^ | ||
| + | | **udevd** | Управление устройствами (см. Глава 3) | | ||
| + | | **journald** | Служба логирования; | ||
| + | | **resolved** | Демон кэширования DNS (см. Глава 9) | | ||
| + | |||
| + | **Примеры программ: | ||
| + | * systemd-udevd (интегрированный в systemd demон udevd) | ||
| + | * systemd-fsck (простая обертка для стандартных системных утилит) | ||
| + | |||
| + | Некоторые программы в / | ||
| + | |||
| + | **Справка: | ||
| + | |||
| + | ===== 6.4. Уровни выполнения в System V ===== | ||
| + | |||
| + | System V init использует **уровни выполнения** (runlevel) для определения состояния машины - число от 0 до 6. Проверить текущий уровень: | ||
| + | |||
| + | <code bash> | ||
| + | who -r | ||
| + | </ | ||
| + | |||
| + | Выход: '' | ||
| + | |||
| + | Уровни выполнения различают состояния: | ||
| + | |||
| + | **Примечание: | ||
| + | |||
| + | ===== 6.5. System V init ===== | ||
| + | |||
| + | System V init - одна из старейших систем инициализации Linux. Устанавливается редко (встречается в RHEL < 7.0, встроенных системах), | ||
| + | |||
| + | Состоит из: | ||
| + | * Конфигурационный файл: '' | ||
| + | * Сценарии загрузки и символические ссылки | ||
| + | |||
| + | ^ Файл ^ Содержимое ^ | ||
| + | | / | ||
| + | | / | ||
| + | | /etc/rc*.d | Каталоги со сценариями (rc1.d, rc2.d и т.д.) | | ||
| + | |||
| + | **Пример строки inittab:** | ||
| + | |||
| + | < | ||
| + | id: | ||
| + | l5: | ||
| + | </ | ||
| + | |||
| + | ^ Действие ^ Назначение ^ | ||
| + | | **initdefault** | Уровень выполнения по умолчанию | | ||
| + | | **wait** | Выполнить команду один раз при входе на уровень, | ||
| + | | **respawn** | Перезапустить команду при выходе (например, | ||
| + | | **ctrlaltdel** | Действие при нажатии Ctrl+Alt+Del (обычно shutdown) | | ||
| + | | **sysinit** | Первое действие при запуске, | ||
| + | |||
| + | ==== 6.5.1. System V init: последовательность команд при запуске ==== | ||
| + | |||
| + | Команда '' | ||
| + | |||
| + | * **S** (Start) - выполнить с аргументом '' | ||
| + | * **K** (Kill) - выполнить с аргументом '' | ||
| + | * **Числа 00–99** - порядок выполнения | ||
| + | |||
| + | **Пример каталога rc5.d:** | ||
| + | |||
| + | < | ||
| + | S10sysklogd | ||
| + | S12kerneld | ||
| + | S15netstd_init | ||
| + | </ | ||
| + | |||
| + | Команда rc выполняет их последовательно: | ||
| + | |||
| + | <code bash> | ||
| + | S10sysklogd start | ||
| + | S12kerneld start | ||
| + | S15netstd_init start | ||
| + | ... | ||
| + | S99sshd start | ||
| + | </ | ||
| + | |||
| + | Сценарии оболочки запускают программы из ''/ | ||
| + | |||
| + | ==== 6.5.2. Ферма ссылок System V init ==== | ||
| + | |||
| + | Содержимое rc*.d - **символические ссылки** на файлы в ''/ | ||
| + | |||
| + | < | ||
| + | lrwxrwxrwx . . . S10sysklogd -> ../ | ||
| + | lrwxrwxrwx . . . S12kerneld -> ../ | ||
| + | lrwxrwxrwx . . . S99httpd -> ../ | ||
| + | </ | ||
| + | |||
| + | Дистрибутивы используют эту **ферму ссылок (link farm)** для переиспользования одних сценариев на всех уровнях выполнения. | ||
| + | |||
| + | === Запуск и остановка служб === | ||
| + | |||
| + | <code bash> | ||
| + | / | ||
| + | / | ||
| + | </ | ||
| + | |||
| + | === Изменение последовательности загрузки === | ||
| + | |||
| + | **Отключить службу без удаления: | ||
| + | |||
| + | <code bash> | ||
| + | mv S99httpd _S99httpd | ||
| + | </ | ||
| + | |||
| + | Префикс '' | ||
| + | |||
| + | **Добавить службу: | ||
| + | |||
| + | ==== 6.5.3. Команда run-parts ==== | ||
| + | |||
| + | Утилита **run-parts** запускает все исполняемые программы в каталоге в определённом порядке. | ||
| + | |||
| + | ^ Дистрибутив ^ Функции ^ | ||
| + | | Fedora | Простая версия - запускает всё подряд | | ||
| + | | Debian/ | ||
| + | |||
| + | Используется в сценариях для массового запуска программ. Большинству пользователей детали неважны. | ||
| + | |||
| + | ==== 6.5.4. Управление System V init ==== | ||
| + | |||
| + | **telinit** - команда управления уровнями выполнения: | ||
| + | |||
| + | ^ Команда ^ Действие ^ | ||
| + | | '' | ||
| + | | '' | ||
| + | | '' | ||
| + | |||
| + | **Предупреждение: | ||
| + | |||
| + | ==== 6.5.5. Совместимость systemd и System V ==== | ||
| + | |||
| + | systemd отслеживает System V сценарии: | ||
| + | |||
| + | 1. Активирует ''< | ||
| + | 2. Идентифицирует скрипты в ''/ | ||
| + | 3. Связывает скрипт со служебным юнитом ('' | ||
| + | 4. Активирует юнит, запускает с аргументом start/stop | ||
| + | 5. Связывает процессы со служебным юнитом | ||
| + | |||
| + | **Результат: | ||
| + | |||
| + | ===== 6.6 Завершение работы системы ===== | ||
| + | |||
| + | Используйте **shutdown** для корректного завершения: | ||
| + | |||
| + | <code bash> | ||
| + | shutdown -h now # Остановить сейчас | ||
| + | shutdown -r +10 # Перезагрузить через 10 минут | ||
| + | </ | ||
| + | |||
| + | ^ Параметр ^ Действие ^ | ||
| + | | **-h** | Halt - остановка и отключение питания | | ||
| + | | **-r** | Reboot - перезагрузка | | ||
| + | | **now** | Немедленно | | ||
| + | | **+n** | Через n минут | | ||
| + | |||
| + | **Перед завершением: | ||
| + | |||
| + | === Процедура завершения === | ||
| + | |||
| + | 1. init просит каждый процесс завершиться | ||
| + | 2. Через время применяет сигнал TERM | ||
| + | 3. Если не помогает - KILL для оставшихся процессов | ||
| + | 4. Блокирует системные файлы | ||
| + | 5. Демонтирует все FS кроме корневой | ||
| + | 6. Ремонтирует корневую FS в режиме read-only | ||
| + | 7. Синхронизирует буфер (sync) | ||
| + | 8. Указывает ядру перезагрузиться/ | ||
| + | |||
| + | **halt/ | ||
| + | |||
| + | ===== 6.7 Начальная файловая система оперативной памяти ===== | ||
| + | |||
| + | **initramfs** - временное пользовательское пространство перед основной загрузкой. Решает проблему: | ||
| + | |||
| + | === Как это работает === | ||
| + | |||
| + | 1. Загрузчик загружает архив с модулями ядра в оперативную память | ||
| + | 2. Ядро распаковывает архив во временную RAM-FS | ||
| + | 3. Утилиты в initramfs загружают необходимые драйверы | ||
| + | 4. Монтируют реальную корневую FS | ||
| + | 5. Запускают полноценный init | ||
| + | |||
| + | ^ Дистрибутив ^ Реализация ^ | ||
| + | | Простые системы | Shell-скрипт, | ||
| + | | systemd системы | Полная systemd без модулей, | ||
| + | |||
| + | === Отключение initramfs === | ||
| + | |||
| + | Если все драйверы встроены в ядро - можно пропустить initramfs. Удалите строку '' | ||
| + | |||
| + | **Примечание: | ||
| + | |||
| + | === Содержимое initramfs === | ||
| + | |||
| + | Распакуйте архив: | ||
| + | |||
| + | <code bash> | ||
| + | unmkinitramfs / | ||
| + | </ | ||
| + | |||
| + | Старые системы использовали **cpio** архивы (см. cpio(1)). | ||
| + | |||
| + | === Создание initramfs === | ||
| + | |||
| + | Обычно создаётся автоматически дистрибутивом. Основные утилиты: | ||
| + | * **mkinitramfs** - простая, | ||
| + | * **dracut** - более мощная | ||
| + | |||
| + | **Примечание: | ||
| + | |||
| + | ===== 6.8 Аварийная загрузка системы и однопользовательский режим ===== | ||
| + | |||
| + | При проблемах с системой используйте **live-образ** дистрибутива или SystemRescueCD на съёмном носителе. Live-образ - полная Linux, загружающаяся без установки. | ||
| + | |||
| + | === Задачи после сбоя === | ||
| + | |||
| + | * Проверка файловых систем | ||
| + | * Сброс забытого пароля | ||
| + | * Исправление критичных файлов (''/ | ||
| + | * Восстановление резервных копий | ||
| + | |||
| + | === Однопользовательский режим === | ||
| + | |||
| + | **Быстрая загрузка в root-оболочку без служб.** | ||
| + | |||
| + | ^ Init система ^ Режим ^ | ||
| + | | System V | Уровень выполнения 1 | | ||
| + | | systemd | rescue.target | | ||
| + | | Параметр загрузчика | **-s** | | ||
| + | |||
| + | **Недостатки: | ||
| + | |||
| + | **Требует: | ||