Что такое планировщик ввода-вывода (I/O scheduler) в Linux?

Ответ

Планировщик ввода-вывода (I/O Scheduler) — это компонент ядра Linux, который определяет порядок выполнения операций чтения/записи (I/O requests), отправляемых на блочное устройство (HDD, SSD). Его главная цель — оптимизировать общую производительность диска и сократить задержки (latency).

Почему это важно для DevOps? Неправильный выбор планировщика может убить производительность базы данных, виртуальной машины или дискового массива.

Основные алгоритмы и когда их использовать:

Планировщик Принцип работы Оптимальное использование
mq-deadline Гарантирует время выполнения для запросов (deadline). Сортирует запросы по LBA (адресу на диске) для минимизации скидинга головки HDD. HDD-диски, гибридные системы. Хороший компромисс между пропускной способностью и задержкой. Часто выбор по умолчанию.
bfq (Budget Fair Queuing) Справедливо распределяет пропускную способность диска между процессами. Полезен для интерактивных десктопов или когда нужно гарантировать время отклика для конкретного приложения. Десктопы, системы, где важна отзывчивость (например, медиа-сервер).
none (или noop для старых ядер) Простая FIFO-очередь. Не выполняет сортировку или переупорядочивание. SSD и NVMe-накопители. У SSD нет механической головки, поэтому сложные алгоритмы сортировки не нужны и только добавляют накладные расходы.
kyber Адаптивный планировщик, фокусируется на сокращении задержек (latency). Разделяет запросы на синхронные (чтение) и асинхронные (запись) и управляет их очередями отдельно. Низколатентные SSD, системы реального времени.

Управление планировщиком:

# 1. Посмотреть доступные и активный планировщик для диска (например, sda)
cat /sys/block/sda/queue/scheduler
# Вывод: [mq-deadline] kyber bfq none
# В квадратных скобках — текущий.

# 2. Изменить планировщик (например, на 'none' для SSD)
echo 'none' | sudo tee /sys/block/sda/queue/scheduler

# 3. Сделать изменение постоянным (через udev правило или параметр ядра)
# Например, добавить в /etc/default/grub: GRUB_CMDLINE_LINUX="scsi_mod.use_blk_mq=1 elevator=none"

Рекомендация: Для серверов с SSD в продакшене часто оптимален none или mq-deadline. Выбор должен подтверждаться бенчмарками под конкретную нагрузку (fio).

Ответ 18+ 🔞

Давай разберемся с этой штукой, которая решает, в каком порядке твой диск будет читать и писать данные. Представь себе бар в пятницу вечером: планировщик ввода-вывода — это такой охранник-вышибала, который решает, кого из гостей (запросов) пустить к стойке (на диск) первым, чтобы не было давки и все получили свой заказ побыстрее.

Зачем тебе, чувак, вообще об этом думать? Да потому что если выбрать не того «вышибалку», твоя база данных или виртуальная машина начнёт тормозить так, что терпения ноль ебать. Всё будет висеть, а ты будешь чесать репу и гадать, в чём же дело.

Вот основные типы этих самых «вышибал» и когда кого ставить:

Планировщик Как работает Куда его пихать
mq-deadline Этот — дисциплинированный, как немец. Он каждому запросу ставит «дедлайн» и старается всех обслужить вовремя. А ещё он умно сортирует заказы, чтобы «официант» (головка диска) бегал по залу (диску) по самому короткому маршруту. Старые добрые HDD (жёсткие диски) или гибридные системы. Золотая середина. Часто стоит по умолчанию, и не просто так.
bfq (Budget Fair Queuing) Этот — справедливый, как коммунист. Он следит, чтобы каждый процесс получил свою законную долю пропускной способности диска. Не даст одному прожорливому приложению сожрать все ресурсы. Десктопы, медиа-сервера — где важно, чтобы система не лагала, пока что-то качается на заднем плане.
none (или noop) А этот — похуист. Его девиз — «да похуй». Пришёл запрос первым — первым и иди. Никакой сортировки, никакой оптимизации. Просто очередь. Вот это — наш выбор для SSD и NVMe! У ссдшек нет механической головки, ей всё равно, в какой сектор писать. Любая «умная» сортировка — это лишняя работа для процессора, овердохуища накладных расходов.
kyber Этот — хитрая жопа, которая помешана на скорости. Он делит запросы на срочные (чтение) и не очень (запись) и крутит ими так, чтобы задержки были минимальными. Быстрые SSD, где каждый микросекунд на счету, или системы реального времени.

Как этим управлять, чтобы не облажаться?

# 1. Сперва глянь, какие планировщики вообще доступны для твоего диска (допустим, sda) и какой сейчас работает.
cat /sys/block/sda/queue/scheduler
# Выдаст что-то вроде: [mq-deadline] kyber bfq none
# В квадратных скобках — активный чувак.

# 2. Хочешь поменять? Например, для SSD ставим 'none'. Просто и эффективно.
echo 'none' | sudo tee /sys/block/sda/queue/scheduler

# 3. Чтобы настройка не слетела после перезагрузки, надо её зафиксировать.
# Например, прописать в параметрах загрузки ядра (в /etc/default/grub): elevator=none
# Потом не забудь update-grub сделать и перезагрузиться.

Итоговая рекомендация, чтоб тебя не ёбнуло: Для сервера с SSD в продакшене чаще всего бери none. Это как снять с бегуна-спринтера (твоего NVMe) тяжеленные ботинки (сложный планировщик). Но если сомневаешься — бенчмарк в помощь! Запусти fio под свою нагрузку и сравни. А то ведь можно и так оптимизировать, что станет только хуже, сам от себя охуеешь.