itmo_conspects

Администрирование в ОС Linux

Операционная система - это базовое системное программное обеспечение, управляющее работой вычислительного узла и реализующее универсальный интерфейс между аппаратным обеспечением, программным обеспечением и пользователем

Возможности по изменению аппаратного обеспечения часто ограничены, поэтому на практике стремятся извлечь максимальную производительность и гибкость за счёт программного обеспечения и грамотного администрирования ОС

Курс разделен на несколько блоков:

  1. Работа с файлами
  2. Файловые системы
  3. Процессы и управление ресурсами
  4. Межпроцессорное взаимодействие
  5. Загрузка операционной системы
  6. Механизмы контейнеризации
  7. Управление пользовательским ПО
  8. Графические среды

Лекция 1. Введение в Linux

Linux (в части случаев GNU/Linux) - это семейство открытых и свободных Unix-подобных операционных систем на базе ядра Linux, включающих набор утилит и программ проекта GNU, а также другие системные и прикладные компоненты

Linux начал своё развитие в 1991 году, когда Линус Торвальдс, будучи студентом Хельсинкского университета, опубликовал первую версию ядра Linux как учебный и исследовательский проект

Со временем вокруг ядра Linux сформировалось большое сообщество разработчиков, а сам Linux стал использоваться в серверах, настольных системах, мобильных и других устройствах

Разделяют бесплатное ПО, открытое ПО и свободное ПО

Бесплатное ПО (Freeware) - программное обеспечение, распространяющееся бесплатно конечному пользователю в виде исполняемых файлов

Открытое ПО (Open-Source Software) - программное обеспечение с открытым исходным кодом, чаще всего распространяющимся по разрешительной лицензии

Свободное ПО (Free and Open-Source Software, FOSS) - открытое программное обеспечение, лицензия которого заставляет авторов производных от него работ лицензировать их под той же свободной лицензией

Linux является свободным программным обеспечением и распространяется под лицензией GNU General Public License 2.0. Это означает, что операционная система Linux гарантирует пользователю 4 свободы, сформулированные Ричардом Столлманом, основателем проекта GNU:

Лицензия GNU General Public License 2.0 накладывает обязательство на то, что производные работы также должны распространяться на условиях этой лицензии

Linux включает набор утилит и программ GNU, такие как Bash или GNU Compiler Collection, которые тоже являются свободным ПО

Linux распространяется не только в виде ядра, но и в виде дистрибутивов - готовых комплектов программного обеспечения, включающих ядро, системные утилиты, менеджер пакетов, установщик и часто графическую среду. Сейчас популярные дистрибутивы - это Debian, Ubuntu, Fedora, Arch Linux и другие

Дистрибутивы Linux бесплатные, но не все. Так, например, Red Hat Enterprise Linux распространяется по платной модели, имея открытый код, но за плату предлагается расширенная корпоративная поддержка и сервис


Ключевые отличия свободного ПО и проприетарного ПО заключаются:


Долгое время наиболее популярной настольной операционной системой остаётся Microsoft Windows. Рассмотрим ключевые концептуальные отличия Linux от Windows:

Лекция 2. Файлы и права доступа

В Linux и других Unix-подобных системах все объекты являются файловыми дескрипторами, то есть все действия совершаются через универсальный интерфейс

Файловый дескриптор - это идентификатор, за которым закреплен определенный поток ввода и вывода. Через файловые дескрипторы в Linux можно работать:

Получаем единый набор операций с файловым дескриптором: открытие, чтение, запись и закрытие

Всего можно выделить 7 типов файлов:


Используя команду ls -l, можно посмотреть на информацию о файлах в каталоге, например:

crw-r--r--   1 root      root       10,   235 Feb 13 17:59 autofs
drwxr-xr-x   2 root      root             180 Feb 13 17:59 block
crw-rw----   1 root      disk       10,   234 Feb 13 17:59 btrfs-control
drwxr-xr-x   3 root      root              60 Feb 13 17:59 bus
drwxr-xr-x   2 root      root            4920 Feb 13 17:59 char
crw-------   1 root      root        5,     1 Feb 13 17:59 console
lrwxrwxrwx   1 root      root              11 Feb 13 17:59 core -> /proc/kcore
drwxr-xr-x  14 root      root             280 Feb 13 17:59 cpu
crw-------   1 root      root       10,   259 Feb 13 17:59 cpu_dma_latency

Первый столбец обозначает тип файла и его модификаторы доступа. Первая буква - это тип файла, так:

Следующие 9 букв задают права доступа для файла. В Linux действует ролевая модель доступа, поэтому есть такие понятия:

Так модификаторы доступа делятся на три тройки букв, каждая тройка из которых показывает права для определенной выборки пользователей

Так -rwxr-xr-x означает регулярный файл, читать и исполнять который могут все, а записывать только владелец

Права доступа проверяются слева направо. Так, если файл имеет права ----r-xr-x, то его владелец не сможет с ним ничего сделать, несмотря на то, что он находится в группе файла

Помимо этих 9 модификаторов есть еще 3 скрытых:

Права можно установить для файла с помощью команды chmod (от change mode):

chmod права файл

Права указываются:

Второй столбец - это число жесткий ссылок на файл

Третий столбец из вывода ls -l указывает на владельца файла, а четвертый - на группу владельца (так как пользователь может состоять в нескольких группах). Сменить владельца можно с помощью команды chown (от change owner):

# меняет владельца на pelmeshke
chown pelmeshke /var/log/mylogs/app.log

# меняет владельца на pelmeshke и группу на supercoolusers
chown pelmeshke:supercoolusers /var/log/mylogs/app.log

# меняет владельца на pelmeshke рекурсивно 
# для всех файлов и каталогов в /var/log/mylogs
chown -R pelmeshke /var/log/mylogs/

По умолчанию, при создании пользователя в Linux ядро создает группу с таким же именем. Для смены группы файла есть команда chgrp (от change group):

# меняет группу на supercoolusers
chgrp supercoolusers /var/log/mylogs/app.log

Лекция 3. Файловые системы

Файловая система - это способ организации информации на носителе данных

Файловая система выполняет такие функции:

Файловая система является посредником в общении между пользователем, использующим ОС, и жестким диском

Позднее число файловых систем стало настолько большим, что в архитектуре операционных систем стала появляется виртуальная файловая система - стандартизованный интерфейс между системными вызовами и конкретной файловой системой

Взаимодействие с хранилищами


Файловые системы могут использовать множество методов организации:

  1. Линейное размещение
  2. Связный список
  3. Таблица аллокаций файлов
  4. Индексные дескрипторы

Подробнее об этом описано в курсе “Операционные системы”

Современные операционные системы используют файловые системы с индексными дескрипторами для дисков, на которых установлена система. Так, Windows использует NTFS (New Technology File System), а для Linux рекомендуется ext4 (от Fourth Extended, Четвертая расширенная файловая система)

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

Поле Тип данных Назначение
s_inodes_count __le32 Общее количество индексных дескрипторов
s_blocks_count_lo __le32 Общее количество блоков (младшие 32 бита)
s_r_blocks_count_lo __le32 Зарезервированные блоки (младшие 32 бита)
s_free_blocks_count_lo __le32 Свободные блоки (младшие 32 бита)
s_free_inodes_count __le32 Количество свободных индексных дескрипторов
s_first_data_block __le32 Первый блок данных
s_log_block_size __le32 Логарифм размера блока в килобайтах по основанию 2
s_log_cluster_size __le32 Логарифм размера кластера в килобайтах по основанию 2
s_blocks_per_group __le32 Блоков в группе
s_clusters_per_group __le32 Кластеров в группе
s_inodes_per_group __le32 Индексных дескрипторов в группе
s_mtime __le32 Время последнего монтирования
s_wtime __le32 Время последней записи
s_mnt_count __le16 Счётчик монтирований после проверки диска
s_max_mnt_count __le16 Максимальное число монтирований, после который нужна проверка диска
s_magic __le16 Магическое число, для ext4 - это 0xEF53
s_state __le16 Состояние файловой системы
s_errors __le16 Поведение при ошибках
s_minor_rev_level __le16 Минорная версия
s_lastcheck __le32 Время последней проверки
s_checkinterval __le32 Интервал проверки
s_creator_os __le32 Операционная система, создавшая раздел (Linux - это 0x0000, FreeBSD - это 0x0003)
s_first_ino __le32 Первый незарезервированный индексный дескриптор
s_inode_size __le16 Размер индексного дескриптора (обычно 256 байт)
s_block_group_nr __le16 Номер группы (для копии суперблока)
s_uuid __u8[16] UUID файловой системы
s_volume_name char[16] Имя тома

… и много других

Здесь __le16, __le32 - беззнаковые целые числа, записанные в Little-endian, размером 16 бит и 32 бита соответственно, __u8[16] - 16-байтный массив беззнаковый 8-битных чисел, а char[16] - символьная последовательность

Источник: https://docs.kernel.org/next/filesystems/ext4/super.html

Со временем появилась идея размещать блоки больших файлов рядом друг с другом, чтобы уменьшать движение читающей головки жесткого диска по секторам

Для решения этого появились группы блоков. Группы содержат свои битовые карты, таблицы индексных дескрипторов и блоки данных

Первая группа под индексом 0 хранит суперблок и таблицу дескрипторов блочных групп (Block Group Descriptors) - структуры с данными полями:

Поле Тип данных Назначение
bg_block_bitmap_lo __le32 Номер блока битовой карты блоков (младшие 32 бита)
bg_inode_bitmap_lo __le32 Номер блока битовой карты дескрипторов (младшие 32 бита)
bg_inode_table_lo __le32 Первый блок таблицы индексных дескрипторов (младшие 32 бита)
bg_free_blocks_count_lo __le16 Количество свободных блоков в группе
bg_free_inodes_count_lo __le16 Количество свободных дескрипторов в группе
bg_used_dirs_count_lo __le16 Количество каталогов в группе
bg_flags __le16 Флаги состояния группы
bg_exclude_bitmap_lo __le32 Блок битовой карты снимков исключения (Exclusion Snapshot)
bg_block_bitmap_csum_lo __le16 Контрольная сумма битовой карты блоков
bg_inode_bitmap_csum_lo __le16 Контрольная сумма битовой карты дескрипторов
bg_itable_unused_lo __le16 Количество неинициализированных индексных дескрипторов
bg_checksum __le16 Контрольная сумма дескриптора группы

… и другие поля

Последующие группы могут хранить также избыточные копии суперблока и таблицы дескрипторов групп, но система будет обращаться к ним в том случае, если начало диска было повреждено

Источник: https://docs.kernel.org/next/filesystems/ext4/group_descr.html

Далее идет битовая карта блоков (Block Bitmap). В ней один бит, равный 1, обозначает, занят ли конкретный блок с тем же индексом

Затем расположена подобная битовая карта для индексных дескрипторов (Inode Bitmap), где бит 1 обозначает, занят ли индексный дескриптор в таблице дескрипторов

Источник: https://docs.kernel.org/next/filesystems/ext4/bitmaps.html

После этого расположена сама таблица индексных дескрипторов. Таблица представляет собой массив дескрипторов, где индекс - это номер индексного дескриптора

Для специальных индексных дескрипторов выделены особые индексы:

9-ый и 10-ый дескрипторы зарезервированы и используются для функций, который обозначены ? в документации, а 11-ый дескриптор - первый не зарезервированный, но обычно используется для каталога /lost+found/, который предназначен для восстановленный утилитой fsck файлов после сбоя

Источник: https://www.kernel.org/doc/html//latest/filesystems/ext4/special_inodes.html

Наконец, после таблицы индексных дескрипторов дальше идут сами блоки данных

Разметка в ext4


В файловой системе ext3 добавилась система журналирования - способ восстановления данных в результате нештатной работы ОС или диска

Всего есть три типа журналов в ext3:

  1. Journal - самый медленный, но самый надежный журнал. Сначала в журнал пишутся блоки данных, потом они копируются в нужное место, а дескриптор изменяется
  2. Ordered - то же самое, но записываем только метаданные файла, что быстрее
  3. Writeback - сначала пишем весь файл, а потом изменяем все метаданные в дескрипторе и журнале

В системе ext4 добавилось много новых функций, которые убирали ограничения старых версий системы:


Хорошей практикой является разделение диска на 6 разделов:

В корневом каталоге Linux создает множество подкаталогов для работы системы, структура которых подчиняется стандарту (FHS) Filesystem Hierarchy Standard:

Filesystem Hierarchy Standard

Лекция 4. Процессы, часть I

Процесс - совокупность набора исполняемых команд, ассоциированных с ним ресурсов и контекста исполнения, находящиеся под управлением операционной системы

Сам же процесс в Linux хранится структурой task_struct с множеством полей, таких как:

В Linux процессы порождаются с помощью других процессов, таким образом, образуя дерево

Дерево процессов

Дерево как структура было выбрано по нескольким причинам:

Первый процесс - это процесс init или systemD, который является корнем одного поддерева процессов

Создание процесса

Для создания процессов могут использоваться три системных вызова:

Жизненный цикл процесса

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

Жизненный цикл процесса в Linux

Подробнее о состояниях процессов описано в курсе “Операционные системы”

Завершение процесса

После того, как процесс окончил исполнения (то есть вызвал системный вызов _exit(status_code)), процесс переходит в состояние “Зомби”. В нем он будет находится до тех пор, пока родительский процесс не прочитает код выхода процесса. Родитель может сделать это несколькими способами:

Демоны

Отдельное место в Linux занимают демоны. Демон (Daemon) - это фоновый процесс, который работает непрерывно и независимо от пользовательской сессии. Он ожидает событий или запросов и обрабатывает их без участия пользователя

Название “демон” происходит из греческой мифологии — демон был фоновым духом, действующим от имени других

Стандартные потоки ввода, вывода и ошибок у демонов перенаправлены в /dev/null. Вместо них демоны используют системный журнал или собственный файл с логами. Также демоны записывают свои идентификаторы процессов, чтобы другие процессы знали, как к ним обратиться

Первый демон, появляющийся при запуске Linux, - это поток [kthreadd] с идентификатором 2. Он является корнем поддерева фоновых потоков ядра, таких как [kswapd0] - демон для страничного обмена, [migration/0] - демон для переноса процессов между ядрами и так далее


Для создания демонов можно:

Лекция 5. Процессы, часть II

Сигнал

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

Сигнал - это сообщение, которое процесс получает от операционной системы или другого процесса. С точки зрения процесса сигнал выглядит как прерывание

Согласно стандарту POSIX, сигналы делятся на стандартные и сигналы реального времени

В Linux всего 31 стандартный сигнал. Рассмотрим самые распространенные из них:

Имя Код Назначение Действие по умолчанию
SIGHUP (от hang up) 1 Процесс завершается, а дочерние процессы получает этот сигнал, чтобы тоже завершиться. Ранее использовался для обозначения прерывания телефонной связи между терминалом и пользователем (дословно “положить трубку”) 🛑
SIGINT (от interrupt) 2 Прерывание выполнения команд от клавиатуры (в терминале вызывается по комбинации Ctrl+C) 🛑
SIGQUIT 3 Прерывание с дампом ядра (обычно Ctrl+\), посылается всем процессам группы 🛑📦
SIGILL (от illegal) 4 Сигнал, посланный ядром, который означает, что выполнявшаяся инструкция является неправильной с точки зрения архитектуры процессора 🛑📦
SIGFPE (от floating point exception) 8 Ошибочная арифметическая операция 🛑📦
SIGKILL 9 Немедленное принудительное завершение процесса 🛑
SIGUSR1 и SIGUSR2 10 и 12 Сигналы, определенные пользователем 🛑
SIGSEGV (от segmentation fault) 11 Нарушение доступа к памяти, например, доступ к еще невыделенной странице 🛑📦
SIGPIPE 13 Процесс написал в именованный канал, но нет процесса, который мог бы прочитать это 🛑
SIGTERM (от terminate) 15 Сигнал завершения 🛑
SIGCHLD, также SIGCLD (от child) 17 Дочерний процесс завершился, был остановлен или продолжил исполнение 🙈
SIGCONT (от continue) 18 Процесс продолжает исполнение ▶️
SIGSTOP 19 Перевод процесса в состояние “Остановлен” ⏸️
SIGTSTR 20 Сигнал остановки с терминала по комбинации Ctrl+Z ⏸️

По умолчанию каждый процесс имеет таблицу обработчиков сигналов, наследованную от первого процесса (init или systemd). Такие обработчики обычно могут совершать такие действия:

Здесь код сигнала указан для архитектур x86 и ARM. В других архитектурах (например, MIPS или SPARC) код сигнала может отличаться

Среди этих все, кроме SIGKILL и SIGSTOP, можно перехватить и переопределить обработчики, например, назначить на SIGINT правильной завершение процесса. На сигналы SIGKILL и SIGSTOP операционная система принудительно убивает или переводит процесс в состояние “Остановлен” соответственно

Сигналы реального времени используются для обычных программ. Они не имеют определенного значения, и всего их может быть до 33 – они определены интервалом от SIGRTMIN (чаще всего 34 или 35) и SIGRTMAX (64). Так как разные имплементации потоков библиотеки glibc используют первые 1 или 2 сигнала для своих задач, рекомендуется использовать SIGRTMIN + 3 вместо 37 или 38

Гарантируется, что сигналы реального времени придут процессу в том же порядке, что они были отправлены. Также, если такой сигнал был послан функцией sigqueue, то процесс-приемник может получить число или указатель на дополнительные данные

Источник: https://www.man7.org/linux/man-pages/man7/signal.7.html

Планирование процессов

Подробнее про планирование процессов описано в курсе “Операционные системы”

За время развития операционной системы Linux существовало множество планировщиков:

В Linux можно выделить 2 типа процессов:

Рассмотрим, как работает Completely Fair Scheduler

Ключевая идея планировщика - каждый процесс должен получать долю процессорного времени, пропорциональную её весу (то есть приоритету). Вместо фиксированных очередей планировщик CFS использует виртуальное время vruntime для каждой задачи

Сами процессы с vruntime должны где-то храниться, причем операции добавления удаления должны быть быстрыми. По этой причине выбрали красно-черное дерево - процессы отсортированы по величине vruntime, а само дерево является самобалансирующимся, то есть в любой момент времени его высота примерно равна log N, а все операции имеют сложность O(log N)

Красно-черное дерево в CFS

Подробнее про CFS: https://www.kernel.org/doc/html/latest/scheduler/sched-design-CFS.html, https://developer.ibm.com/tutorials/l-completely-fair-scheduler/
Исходный код CFS: https://github.com/torvalds/linux/blob/v6.5/kernel/sched/fair.c


Completely Fair Scheduler полагался на множество эвристик и параметров, чтобы корректно работать с интерактивными и фоновыми задачами

Новый алгоритм Earliest eligible virtual deadline first вместо этого имеет математический подход. В нем есть три понятия:

На каждом шаге EEVDF:

Однако процессы могут кратковременно засыпать, чтобы повышать свой лаг, что делает планировщик несправедливым. Чтобы бороться с этим, планировщик не убирает такие задачи из очереди “Готовность”, а также меньше уменьшает их лаг

Статья про EEVDF: https://citeseerx.ist.psu.edu/document?doi=805acf7726282721504c8f00575d91ebfd750564&repid=rep1&type=pdf
Документация про EEVDF: https://docs.kernel.org/scheduler/sched-eevdf.html

Псевдофайловая система /proc/

Для доступа к сведениям процессов есть псевдофайловая система /proc/, которая представляет из себя набор файлов для каждого процесса. При чтении одного из файлов в этом подкаталоге данные достаются не из диска, а из оперативной памяти

Директория /proc/ содержит множество поддиректорий вида /proc/<PID> с числовыми названиями. Это число представляет из себя идентификатор процесса, а поддиректория хранит информацию о процессе, а именно:


Помимо информации для каждого процесса /proc/ хранит общую информацию об операционной системе

Лекция 6. Загрузка ОС Linux

Каждый раз, когда пользователь нажимает кнопку питания своего компьютера, до того, как система полностью будет загружена, происходят несколько ключевых этапов:

Загрузка BIOS/UEFI

Сначала запускается BIOS - Basic Input/Output System (Базовая система ввода/вывода). BIOS не является полноценной операционной системой: это прошивка материнской платы, которая выполняет начальную инициализацию оборудования и передает управление загрузчику. В начале запуска компьютера BIOS проводит процедуру POST (Power-On Self-Test) - проверяет работоспособность оборудования (процессора, ОЗУ и так далее)

BIOS узнает о загрузочном коде напрямую из таблицы MBR (Master Boot Record, Главная загрузочная запись), которая расположена в начале любого диска, с которого можно загрузится (или через PXE - Preboot eXecution Environment)

Master Boot Record занимает первый 512 байт (первый сектор на диске) и содержит:

Сейчас же вместо BIOS повсеместно используется UEFI - Unified Extensible Firmware Interface (Единый расширяемый интерфейс прошивки). UEFI - это более современная прошивка, которая поддерживает графический интерфейс, управление мышью и обычно работает с таблицей разделов GPT (GUID Partition Table)

Программный код BIOS и UEFI расположены непосредственно на микросхеме на материнской плате компьютера

Загрузчик GRUB

Далее рассмотрим загрузку Linux в BIOS. BIOS загружает выбранный исполняемый код, который находится в MBR, в ОЗУ, и процессор исполняет его. Для загрузки Linux используют особой компонент - загрузчик. Сейчас самый используемый - это GNU GRUB (GRand Unified Bootloader) версии 2

BIOS

Код из Master Boot Record содержит 1 фазу загрузчика GRUB boot.img - он занимает 440 байт, что недостаточно для полноценной загрузки

boot.img далее запускает фазу 1.5 загрузчика - core.img. Он находится между MBR и первым разделом диска, в нем расположен код базового набора драйверов для файловых систем (ext4, xfs и так далее), для работы с массивом RAID или LVM (Logical Volume Manager, менеджер логических томов). Как правило, размер core.img составляет от 30 до 40 Кб (как правило 62 сектора на диске, максимальный размер - 458 240 байт)

После этого core.img уже может читать файлы из раздела загрузчика (после загрузки он монтируется как /boot/grub и как правило, находится на другом разделе, чем /). core.img загружает код загрузчика из /boot/grub, который прочитывает файл grub.cfg, где находится выбор ОС (в случае Linux это выбор ядра или его версии) - так начинается фаза 2. GRUB запускает графическое меню, где можно выбрать ядро и его параметры:

Меню GRUB

UEFI

Для компьютеров с UEFI все намного проще. UEFI является намного более умным, чем BIOS, и его память на материнской плате содержит драйвера для работы с дисками (в частности для файловых систем FAT16 и FAT32), устройствами USB и сетью

Также UEFI хранит загрузочные записи - они хранят идентификатор GUID раздела и путь до кода загрузчика в специальном разделе ESP (EFI System Partition)

Далее при запуске UEFI ищет на диске этот скрытый раздел ESP, который отформатирован в FAT16 или FAT32. На этом разделе хранятся загрузчики разных ОС и другие инструменты (например, для проверки памяти или для отладки ядра)

При загрузке Linux этот раздел монтируется в /boot/EFI. Структура этого каталога выглядит примерно так:

/boot/EFI
├── ARCH
│   └── grubx64.efi
├── BOOT
│   ├── BOOTIA32.EFI
│   ├── BOOTX64.EFI
│   ├── fbia32.efi
│   └── fbx64.efi
├── Microsoft
│   ├── Boot
│   │   ├── bootmgfw.efi
│   │   ├── bootmgr.efi
│   │   ├── boot.stl
│   │   ├── memtest.efi
│   │   ├── SecureBootRecovery.efi
│   │   └── ...
│   └── Recovery
│       └── ...
└── systemd
    └── systemd-bootx64.efi

Главный загрузчик для Windows, Windows Boot Manager, находится в файле Microsoft/bootmgfw.efi. Для Linux (в данном случае дистрибутива Arch Linux) загрузчик расположен в ARCH/grubx64.efi. В BOOT лежит загрузчик по умолчанию: операционная система сначала создает свой загрузчик в BOOT, затем копирует его в отдельную директорию и создает запись в памяти UEFI

Сам файл grubx64.efi представляет собой код из core.img - набор базовый модулей, необходимый для чтения раздела в ext4, конфигурационного файла grub.cfg и загрузки дополнительных модулей

Помимо этого UEFI еще может загружаться через сеть. Для этого он, предварительно получив IP-адрес по протоколу DHCP, скачивает по протоколу TFTP файл bootx64.efi и запускает его

Загрузка ядра

После выбора записи загрузчик GRUB помещает в память образ ядра Linux vmlinuz и образ начальной файловой системы initramfs, а затем передает управление ядру

Сам файл vmlinuz - это сжатый образ ядра. Исторически название расшифровывают как vm (virtual memory, виртуальная память) + linu (linux) + z (zipped - сжатый образ). В оперативной памяти ядро распаковывается, переходит в защищенный режим работы процессора, настраивает таблицы страниц, обработчики прерываний, планировщик и начинает обнаружение устройств

На этом этапе ядро еще не может сразу смонтировать настоящую корневую файловую систему /, потому что для этого часто нужны дополнительные модули и драйверы

Именно поэтому вместе с ядром загружается initramfs (от Initial RAM Filesystem) - небольшой архив, который распаковывается в оперативную память и превращается во временную корневую файловую систему

Внутри initramfs обычно находятся:

Раньше до версии ядра 2.6 вместо initramfs использовался initrd (Initial RAM Disk), который монтировался как блочное устройства

Обычно дальше идут такие процессы:

  1. Ядро распаковывает initramfs в память
  2. Запускается ранняя пользовательская программа /init. /init загружает нужные модули ядра и подготавливает устройства
  3. Находится и монтируется настоящий корневой раздел. Затем выполняется переключение корня из initramfs, который находится в ОЗУ, в файловую систему раздела на диске
  4. Управление передается уже обычной системе в корневом разделе

Если корневой раздел недоступен, система часто попадает в аварийную оболочку из initramfs, где администратор может вручную диагностировать проблему

Система инициализации

Когда настоящее корневое дерево каталогов уже доступно, ядро запускает первый пользовательский процесс с идентификатором PID = 1. Исторически это была программа init, а в современных дистрибутивах чаще всего таким процессом становится systemd

Процесс PID = 1 - это особый процесс, так как:

Если ядро не может запустить процесс с PID = 1, загрузка прекращается с паникой ядра


Классическая система инициализации init, которая появилась в UNIX System III и получила развитие в UNIX System V (сейчас такой init называют SysV init), использовала набор sh-скриптов из каталогов вида /etc/rc*.d/. Они запускались последовательно в соответствии с выбранным уровнем выполнения (так называемым runlevel), который описаны в /etc/inittab.Формат строк в /etc/inittab такой:

<идентификатор>:<уровни исполнения>:<действие>:<командная строка запуска>

В System V уровни выполнения в init были такими:

В распространенных дистрибутивах, таких как Debian, уровни означали другое:

Уровень 1 обычно предназначен для загрузки ОС и ее восстановления

В файле /etc/inittab поле <действие> определяет режим запуска процесса, например: wait - запустить и ждать завершения, respawn - перезапускать после завершения, sysinit - выполнить на раннем этапе загрузки


В большинстве современных дистрибутивов вместо SysV init используется systemd. Он запускает службы параллельно, использует декларативные файлы вида /etc/systemd/system/myapp.type и умеет отслеживать зависимости между компонентами системы

Службы в systemd имеют тип:

Тип службы определяет показывает, какой объект системы он описывает. Так, /etc/systemd/system/myapp.service - это служба. Внутри текстовый файл содержит ее описание:

[Unit]
Description=My Application
After=network.target        # запустить после запуска демона networkd

[Service]
Type=simple
User=myappuser              # запустить от имени myappuser
ExecStart=/usr/bin/myapp    # исполняемый файл
Restart=on-failure          # перезапустить при падении
StandardOutput=journal      # записывать логи в журнал systemd

При загрузке systemd читает конфигурацию, монтирует файловые системы, поднимает сеть, запускает системные службы и доводит систему до нужного целевого состояния, например до multi-user.target (многопользовательский режим) или graphical.target (режим с графической оболочкой)


Подытоживая, загрузку ОС Linux можно описать так:

Загрузка ОС Linux

Последовательность загрузок разных частей операционной системы расширяет функционал до тех пор, пока система может взаимодействовать с оборудованием, и решает проблему “курицы и яйца”

X. Программа экзамена 2025/2026

  1. Отличия ОС семейства GNU/Linux от других ОС с точки зрения администрирования.
  2. Понятие файла в операционных системах GNU/Linux. Типы файлов. Атрибуты файлов.
  3. Управление правами доступа к файлам и директориям.
  4. Организация файловых систем в ОС GNU/Linux: особенности файловых систем ext2, ext3, ext4.
  5. Структуры данных файловых систем ext3, ext4: структура группы блоков; структура суперблока; структура индексного дескриптора.
  6. Монтирование файловых систем. Ручное и автоматическое монтирование.
  7. Понятие процесса в GNU/Linux. Рождение процесса.
  8. Процессы-демоны. Сигналы.
  9. Отображение структур данных о процессе в псевдофайловую систему /proc/
  10. Загрузка операционной системы Linux: Организация работы загрузчика. Загрузка ядра. Стартовый виртуальный диск.
  11. Загрузка операционной системы GNU/Linux по модели System V: стандартный процесс init: структура файла inittab, условия выполнения команд, уровни выполнения, скрипты sysinit и rc.
  12. Запуск ОС GNU/Linux по моделям UpStart и SystemD.
  13. Установка пользовательского программного обеспечения в операционных системах GNU/Linux. Способы установки, их отличия и области применения.
  14. Установка пользовательского ПО из исходного кода.
  15. Пакетная установка пользовательского ПО: внутреннее устройство пакетов Debian.
  16. Пакетная установка пользовательского ПО: внутреннее устройство пакетов RPM.