ServerAdmin.ru
31K subscribers
573 photos
46 videos
22 files
2.83K links
Авторская информация о системном администрировании.

Информация о рекламе: @srv_admin_reklama_bot
Автор: @zeroxzed

Второй канал: @srv_admin_live
Сайт: serveradmin.ru

Регистрация в РКН: https://vk.cc/cG1Urj
Download Telegram
Тема тестирования производительности диска непростая. Если есть время и чёткая задача, то с помощью fio и продолжительного времени на тесты, можно добиться стабильного результата. А если хочется быстро оценить работу диска и сравнить результат, то возникают вопросы даже с самым простым тестом на последовательную запись.

Я попытался немного разобраться с этой темой и сделал ряд тестов в виртуальных машинах. Основные сложности тут следующие:

1️⃣ Если просто писать данные на диск с уровня операционной системы Linux, то она будет их кэшировать, пока у неё достаточно оперативной памяти для этого. Если не учитывать этот момент, то результаты будут разными в зависимости от объёма оперативной памяти и размера записываемых данных.

2️⃣ Если речь идёт о виртуальных машинах, то там есть слой кэширования гипервизора.

3️⃣ Если используется аппаратный рейд контроллер, то там есть свой слой кэширования, плюс запись в несколько потоков может идти быстрее, чем в один.

На практике это выглядит так. Берём виртуальную машину на Proxmox с 1G оперативной памяти и виртуальным диском без кэширования. Пробуем тесты на запись с помощью dd и разных флагов:

# dd if=/dev/zero of=/tempfile bs=1M count=512
259 MB/s

# dd if=/dev/zero of=/tempfile bs=1M count=2000
247 MB/s

# dd if=/dev/zero of=/tempfile bs=1M count=2000 oflag=direct
240 MB/s

# dd if=/dev/zero of=/tempfile bs=1M count=2000 oflag=dsync
123 MB/s

# dd if=/dev/zero of=/tempfile bs=1M count=2000 oflag=sync
123 MB/s

Используются флаги:

▪️direct - прямая запись в обход файлового кэша и синхронизации
▪️dsync - запись данных с синхронизацией каждого блока, то есть ждём подтверждение диска об успешной записи
▪️sync - запись данных и метаданных с синхронизацией

Результаты меня удивили. Я всегда был уверен, что запись dd по умолчанию будет вестись в кэш ОС, если хватает оперативной памяти. Я провёл много тестов на разных виртуалках, в разных гипервизорах, с разным количеством памяти в VM. И везде запись нулей из /dev/zero на диск в кэш не попадала. Из-за большого количества тестов глаз замылился, и я не мог понять, в чём причина. Подумал уже, что по дефолту dd работает с флагом direct, но это не так.

Причина вот в чём. Если файл /tempfile уже существует, то запись ведётся напрямую, а если отсутствует и оперативы достаточно, то в кэш. Проверяем:

# dd if=/dev/zero of=/tempfile bs=1M count=200
231 MB/s
# rm /tempfile
# dd if=/dev/zero of=/tempfile bs=1M count=200
635 MB/s

Если взять ещё меньше файл, то скорость будет ещё больше:

# rm /tempfile
# dd if=/dev/zero of=/tempfile bs=1M count=100
1.6 GB/s

Если вы будете писать с помощью dd обычный файл, который полностью помещается в оперативную память, то тоже при первичной записи файл попадёт в кэш:

# dd if=/tempfile of=/tempfile2 bs=1M count=128
910 MB/s

Всё было записано в кэш. Скорость диска мы вообще не увидели. Для тестирования линейной скорости записи на диск обязательно используйте флаг direct или sync. Значения вы получите разные в зависимости от флага, но они точно будут без использования кэша ОС.

А теперь я включу кэширование диска (Write back) на уровне гипервизора и выполню тесты с direct:

# dd if=/dev/zero of=/tempfile bs=1M count=2000 oflag=direct
1.0 GB/s

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

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

❗️Если при тестах диска вы видите очень большой разброс в значениях, у вас 100% где-то что-то залетает в кэш. Я не раз слышал от знакомых и читателей замечания по этому поводу. Люди получают сильно разные результаты тестов и не понимают, как их интерпретировать. Могут из-за этого ошибочно посчитать одно хранилище или формат диска быстрее другого.

#linux #disk
Продолжу начатую недавно тему про заметание следов своей деятельности в системе на базе Linux. Пишу не для того, чтобы вы заметали за собой следы, а чтобы понимали, как от этого защищаться. Сегодня речь пойдёт про управление датами создания и изменения файлов.

В Linux это достаточно просто сделать, если есть соответствующие права. В связи с этим расследование инцидентов без наличия бэкапа зачастую становится невыполнимой задачей. Невозможно наверняка узнать, какие файлы изменял злоумышленник. Если нет бэкапа исходников того же сайта, вычищение деятельности зловреда усложняется кратно, так как нет эталона для сравнения. Даты изменения файлов уже не подходят.

Напомню, что у файла есть несколько меток времени:

▪️Birth (crtime) - время создания айноды файла, то есть самого файла.
▪️Access (atime) - время последнего доступа к файлу.
▪️Modify (mtime) - время последнего изменения содержимого файла.
▪️Change (ctime) - время последнего изменения метаданных файла в файловой системе.

Посмотреть указанные метки можно командой stat:

# stat testfile

Поменять значения atime и mtime крайне просто. Можно взять банальную утилиту touch:

# touch -m -a -t 202501010000 testfile
# stat testfile
Access: 2025-01-01 00:00:00.000000000 +0300
Modify: 2025-01-01 00:00:00.000000000 +0300

То же самое можно сделать напрямую в файловой системе через debugfs:

# debugfs -w -R 'set_inode_field /var/www/testfile crtime 202501010000' /dev/sda1
# debugfs -w -R 'set_inode_field /var/www/testfile atime 202501010000' /dev/sda1
# debugfs -w -R 'set_inode_field /var/www/testfile mtime 202501010000' /dev/sda1
# debugfs -w -R 'set_inode_field /var/www/testfile ctime 202501010000' /dev/sda1
# echo 2 > /proc/sys/vm/drop_caches
# stat /var/www/testfile
Access: 2025-01-01 03:00:00.881765992 +0300
Modify: 2025-01-01 03:00:00.881765992 +0300
Change: 2025-01-01 03:00:00.881765992 +0300
Birth: 2025-01-01 03:00:00.881765992 +0300

В конце для проверки надо обязательно сбросить кэш, иначе изменений не увидите. Важно понимать, что для изменения atime и mtime достаточно обычных прав доступа к файлу. То есть любой червь, который залез через исходники сайта, может у него менять эти параметры. А вот для изменения crtime уже нужны права root, так как надо лезть в файловую систему.

Помимо прочих средств защиты, конкретно в данной ситуации с файлами может помочь аудит доступа с помощью auditd.

# apt install auditd
# auditctl -w /var/www/testfile -p rwa -k testfile_rule

◽️rwa - чтение (r), запись (w), изменение атрибута (a)
◽️testfile_rule - название правила аудита

Смотрим список правил:

# auditctl -l
-w /var/www/testfile -p rwa -k testfile_rule

После изменения файла смотрим записи аудита:

# aureport -f -i | grep /var/www/testfile
# ausearch -i -k testfile_rule

Лог аудита хранится в директории /var/log/audit. Поддерживается работа через syslog, так что при желании этот лог выносится на внешний сервер, как я уже рассказывал в предыдущих заметках. Подобный аудит больше актуален для конфигурационных файлов служб, в том числе системных, а не исходников сайтов. Я просто показал пример.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #terminal
Прочитал интересную статью про Linux IOWait в блоге компании Percona. У автора оказались подозрительно русские имя и фамилия - Peter Zaitsev. Навёл справки. Оказалось, что это Пётр Зайцев - сооснователь компании Percona. Я и не знал, что эта компания основана русскими, хотя пользуюсь её бесплатными продуктами много лет.

Understanding Linux IOWait

Сделал короткую выжимку из статьи, чтобы передать суть. Информация показалась полезной и новой для меня. Вначале пример от автора, как можно жёстко нагрузить дисковую подсистему:

# sysbench --threads=8 --time=0 --max-requests=0 fileio --file-num=1 --file-total-size=10G --file-io-mode=sync --file-extra-flags=direct --file-test-mode=rndrd run

Используется утилита sysbench. Я, кстати, писал про неё. У неё есть встроенные тесты для СУБД. Приведённая выше команда жёстко нагрузит метрику cpu iowait. Проверить можно через vmstat, колонка wa.

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

# sysbench --threads=8 --time=0 cpu run

Снова смотрим на vmstat и видим, что нагрузка IOWait куда-то пропала. Как так? Первый тест продолжает нагружать диски, но мы уже этого не видим в привычной метрике.

Смысл тут вот в чём. Когда мы долго ждём ответа от дисков, процессор простаивает. Растёт метрика cpu idle. Простой процессора из-за ожидания I/O засчитывается в метрику IOWait. Но как только мы нагружаем процессор другой работой, метрика idle падает, а за ней и IOWait. Это особенность подсчёта этих метрик.

Теперь вместо первого теста в 8 потоков, запустим только один на виртуалке с 4-мя ядрами:

# sysbench --threads=1 --time=0 --max-requests=0 fileio --file-num=1 --file-total-size=10G --file-io-mode=sync --file-extra-flags=direct --file-test-mode=rndrd run

Несмотря на то, что этот тест тоже полностью нагрузит дисковую подсистему, мы увидим IOWait в районе 20-25%. А на виртуальных машинах с большим числом ядер (32-64) цифра будет настолько незначительна, что мы можем вообще не заметить её. Но при этом дисковая подсистема будет полностью загружена.

Таким образом, высокая метрика IOWait показывает, что процессор ожидает операции I/O. Но при этом низкий показатель не гарантирует, что у вас не загружены диски. Надо уточнять.

Как же узнать, что у нас есть проблемы с нагрузкой по I/O? Можно посмотреть на столбец b в vmstat. Он показывает количество процессов, которые заблокированы в ожидании I/O для завершения. Соседний столбец r покажет суммарное число запущенных процессов.

В продукте Percona Monitoring and Management есть плагин, который в том числе показывает статистику по процессам. Там будут видны процессы, ожидающие I/O. Указанный мониторинг бесплатен, это open source.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #perfomance
Тестировал вчера open source панель для управления сервером и установки на него софта - Cosmos. Сам автор позиционирует её как Secure and Easy Selfhosted Home Server. Панель и сама работает в Docker, и софт запускает тоже в контейнерах. Это уже не первая подобная панель на канале. Сразу скажу, что ничего особенного в ней не увидел. Она не лучше и не проще всех остальных похожих.

В целом, пользоваться можно. Даже русский язык есть, но переведено кривовато. Я переключился на английский. У всех подобных панелей на базе Docker есть один существенный минус. Они хоть и позиционируют себя как простые и быстрые в настройке, на деле это не так. Запуск приложений в Docker, особенно когда их много на одном сервере, требует от пользователя понимания, как всё это между собой связано и работает. Постоянно возникают небольшие нюансы в работе, которые не решить без этих знаний. А если вы знаете Docker, то и панель вам особо не нужна. Ставишь Portainer и запускаешь всё там.

Cosmos в целом неплоха в сравнении с остальными. Выделю несколько полезных особенностей:

▪️Интерфейс адаптивен, работает и на мобильных устройствах.
▪️Можно создавать пользователей веб панели. Бесплатная версия позволяет создать 5 штук.
▪️Панель нативно поддерживает работу MergerFS и SnapRAID.
▪️Из коробки HTTPS от Let's Encrypt.
▪️Поддержка OAuth 2.0 и OpenID, 2FA через Google аутентификатор или аналоги.
▪️Есть встроенные средства безопасности, на основании которых можно ограничивать доступ к публикуемым ресурсам. Можно ограничивать доступ на основе групп. Блокировать ботов, тех, кто превышает лимиты по запросам или трафику.

Запустить и посмотреть на Cosmos можно так:

# docker run -d --network host --privileged --name cosmos-server -h cosmos-server --restart=always -v /var/run/docker.sock:/var/run/docker.sock -v /var/run/dbus/system_bus_socket:/var/run/dbus/system_bus_socket -v /:/mnt/host -v /var/lib/cosmos:/config azukaar/cosmos-server:latest

Если настроено доменное имя, то можно сразу получить сертификат от Let's Encrypt, а все устанавливаемые службы будут запускаться на поддоменах. Если же сделать установку без HTTPS по IP адресу сервера, то сервисы будут подниматься на отдельных TCP портах. Я и так, и так попробовал.

Аналоги Cosmos:

◽️CasaOS
◽️Runtipi

Мне лично CasaOS больше всего понравилась. Она более целостно смотрится, магазин приложений больше, как и в целом сообщество. Но Cosmos более функциональна в базе.

🌐 Сайт / Исходники / Demo

#docker #linux
При использование популярной в Linux утилиты ps чаще всего оперируешь PID процесса или грепаешь вывод по строке в имени процесса:

# ps -p 524 -o %mem,%cpu,cmd
# ps ax | grep prometheus

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

# ps -T -C prometheus
  PID  SPID TTY     TIME CMD
  525   525 ?    00:55:34 prometheus
  525   803 ?    00:03:10 prometheus
  525   808 ?    00:09:22 prometheus
  525  1054 ?    00:08:44 prometheus
  525  1113 ?    00:12:03 prometheus
  525  1129 ?    00:10:42 prometheus
  525  58983 ?    00:11:30 prometheus

Увидели сразу PID процесса 525 и все его потоки с номерами SPID. Иногда бывает нужно посмотреть или сразу посчитать потоки во время отладки какого-то приложения, которое, к примеру, виснет по какой-то причине. Быстро считаем его потоки:

# ps -T -C zabbix_server | wc -l
82

Обращаю внимание, что вывод с потоками будет больше, чем просто вывод списка процессов, которые тоже часто считают для задач мониторинга. На том же сервере в тот же момент:

# ps ax | grep zabbix_server | wc -l
59

Если есть какие-то проблемы с приложением, и не понятно, что именно тормозит, можно вывести нужные метрики с разбивкой на потоки. Это хорошо показать на примере Fail2ban с PID 508.

# ps -L -o spid,%mem,%cpu,cmd 508
SPID %MEM %CPU CMD
  1070 0.6 0.0 /usr/bin/python3 /usr/bin/fail2ban-server -xf start
  1071 0.6 0.1 /usr/bin/python3 /usr/bin/fail2ban-server -xf start
  1072 0.6 0.0 /usr/bin/python3 /usr/bin/fail2ban-server -xf start
  1074 0.6 0.1 /usr/bin/python3 /usr/bin/fail2ban-server -xf start
  1075 0.6 0.0 /usr/bin/python3 /usr/bin/fail2ban-server -xf start
  1077 0.6 0.3 /usr/bin/python3 /usr/bin/fail2ban-server -xf start

У Fail2ban может быть много фильтров, которые обрабатываются в разных потоках. И какой-то из них в случае лавинообразного разрастания лога может очень сильно нагружать систему. Зная PID и SPID можно посмотреть подробности потока:

# cat /proc/508/task/1077/stat
1077 (f2b/f.wp-login) ...................................

Всю строку не привожу, так как самое интересное в начале. Тут видно, что указанный поток обрабатывает jail с именем wp-login. Больше информации покажет status:

# cat /proc/508/task/1077/status

Ещё более подробную информацию можно получить через strace. Он не только по PID может подключаться, но и по SPID:

# strace -p 1077

Там будет виден и лог, который поток читает, и даже конкретные строки. На нагруженном сервере завалит консоль, так что лучше сразу в файл выводить и потом смотреть. Обычное перенаправление в файл не сработает, надо использовать ключ -o:

# strace -p 1077 -o ~/strace.out

Можно конкретизировать, что записывать. Например, для Fail2ban будут актуальны операции открытия файлов и чтения:

# strace -p 1077 -e trace=openat,read

А для каких-то процессов будет иметь смысл следить за записью:

# strace -p 1077 -e trace=write

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

Трейсы в режиме реального времени можно посмотреть и в htop. Выбираете нужный процесс или поток и нажимайте s. Если strace установлена в системе, то увидите её работу.

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

📌 Полезные ссылки по теме заметки дебага консольными утилитами:
▪️Примеры использования ps
▪️Анализ дисковой активности в Linux
▪️Узнаём, что конкретно тормозит в php коде
▪️Расследование фантомных чтений с диска
▪️Расследование тормозов php сайта с помощью perf
▪️Профилирование нагрузки в Linux
▪️Кто и как использует swap
▪️Анализируем нагрузку на диск с помощью perf-tools

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #terminal #perfomance
Я в консоли Linux настройки IP адресов уже давно привык смотреть так:

# ip a

На выходе получается что-то похожее на ifconfig, только с другим форматированием. Ifconfig давно уже не ставлю и не использую. Все ключи позабыл. Смысла в ней уже нет с повсеместным распространением утилиты ip.

На прошлой неделе смотрел одного блогера и мельком увидел, как он смотрит IP адреса сервера:

# ip -br a
lo         UNKNOWN    127.0.0.1/8 ::1/128 
eth0        UP        172.18.107.235/20 fe80::215:5dff:fe0d:7101/64 
eth1        UP        192.168.101.2/24 fe80::215:5dff:fe0d:7105/64 
docker0      DOWN       172.17.0.1/16 
br-e901d734a0f3 DOWN       172.18.0.1/16 

Конкретизируем только IPv4:

# ip -br -4 a
lo         UNKNOWN   127.0.0.1/8 
eth0        UP       172.18.107.235/20 
eth1        UP        192.168.101.2/24 
docker0      DOWN      172.17.0.1/16 
br-e901d734a0f3 DOWN      172.18.0.1/16

Очень удобно. Я не знал и нигде не видел этот ключ. Сразу себе записал и постарался запомнить. Так реально удобнее смотреть. Сразу все адреса на виду, не надо глазами искать конкретный адрес в куче других строк.

Для просмотра линков и mac адресов ключ тоже применим:

# ip -br l
# ip -br n

Для справки ещё одну команду добавлю, которую тоже постоянно выполняю. Просмотр маршрутов:

# ip r

Вообще, использование ip упростило вопросы просмотра и управления сетевыми настройками, так что довольно легко и добровольно на неё переключился в своё время. Где-то наверное со времён Centos 7.

Интересно, кто-то ещё ставит специально ifconfig и использует? Её вроде выпилили из базовых наборов системных утилит.

#linux #terminal
Одним из самых популярных репозиториев на github (21-е место по кол-ву звёзд) является репозиторий с ohmyzsh. Это фреймворк для создания конфигураций оболочки zsh. Для тех, кто не понимает, что это такое, скажу просто. Это сильно прокачанный по функциональности bash.

Никогда не понимал страсти и большой народной любви к zsh и ohmyzsh в частности. Хотя несколько раз пробовал. У меня и на рабочей станции, и на серверах всегда обычный bash. Мне кажется такое единообразие удобнее.

Если захотите попробовать zsh c ohmyzsh, то сделать это можно так:

# apt install zsh
# wget https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh
# sh install.sh

Дальше поверх этого делаются различные настройки

Основные возможности ohmyzsh:

◽️Поддержка тем для консоли и промта в частности. Причём тем не только по изменению внешнего вида, но и в плане функциональности: отображение ветки git, таймер выполнения текущей команды и другие возможности.

◽️Большой набор готовых плагинов. Они могут добавлять алиасы, включать автодополнение при наборе команд, к примеру, от docker, git, kubectl, ansible и т.д. Там есть интеграции с менеджерами паролей, с screen и tmux, с батареей ноутбука. Чего там только нет.

В общем, ohmyzsh открывает безграничный простор для изменения и настройки командной строки. Мне это напоминает времена, когда были очень популярный виджеты в Windows. Я время от времени ковырялся в них, настраивал какую-то красоту и удобство. Через неделю все всё это надоедало и я убирал.

С ohmyzsh то же самое. Я аналог этой оболочки даже на виндовый терминал сталвил – oh-my-posh. Потом надоело, убрал. Отзывчивость консоли падает. Все эти расширения и плагины какие-то ресурсы забирают и добавляют задержку. В итоге ни zsh, ни его расширения у меня так и не прижились.

А вы используете эти украшательства или предпочитаете обычный bash? Я даже promt в нём не меняю, оставляю стандартный user@hostname.

#terminal #linux
Для просмотра дерева запущенных процессов в системе Linux можно использовать разные способы. Я давно знаю 2 из них и постоянно применяю:

1️⃣ В утилите htop, которую я всегда ставлю на сервера под своим управлением, есть режим древовидного отображения процессов. Для этого надо нажать клавишу t (tree view). Это удобно, когда в моменте надо что-то быстро посмотреть. Если процессов много и надо вдумчиво изучить список, то в htop не очень удобно из-за того, что интерфейс интерактивный.

2️⃣ Консольная команда ps axf, а если список большой то она же, но направленная в текстовый файл ps axf > ~/ptree.txt. Там уже можно более спокойно и осмысленно всё посмотреть.

На днях просматривал репозиторий the-art-of-command-line. Там в основном информация для новичков. Большую часть я и так знаю, но нашёл для себя кое-что новое.

3️⃣ Есть программа pstree в составе пакета psmisc. Он во многих системах есть в базовом наборе системных утилит, либо ставится из стандартных репозиториев. С помощью pstree можно вывести древовидный список процессов в наглядном виде. Нагляднее, чем у ps.

# pstree -p

Есть ещё пара полезных ключей:

-t – показывает полные имена подпроцессов. Для некоторых служб показывает чуть больше информации.
-n – сортировка по pid, а не имени.
-С age – раскраска имён процессов по возрасту. Процессы новее 60 секунд выводятся зелёными, новее часа – жёлтыми, а остальные красными.

Посмотрел все остальные ключи, полезными их не нашёл.

Берите на вооружение, если как и я не знали о существовании этой утилиты.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #terminal
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
Когда-то давно писал про одну полезную консольную команду, которой иногда пользуюсь. Она принудительно и моментально отправляет сервер с Linux в перезагрузку. Эффект аналогичен нажатию на кнопку reset:

# echo b > /proc/sysrq-trigger

Разница с консольными командами reboot или shutdown как минимум в том, что они обычные бинарники на диске.

# type reboot
reboot is /usr/sbin/reboot

# type shutdown
shutdown is /usr/sbin/shutdown

Хотя на самом деле это уже давно не бинарники, а только ссылки на /bin/systemctl, но это не отменяет того, что последний тем не менее исполняемый файл. Он должен существовать, а во время выполнения пошуршать диском. У него куча ссылок на таргеты и службы systemd.

Если с диском какие-то проблемы, либо он загружен так, что ни на что не отвечает, штатный reboot не состоится, либо будет долго исполняться. К тому же reboot пытается корректно отключить примонтированные диски. Очевидно, что если с одним из них проблемы, то тоже будет всё тупить и подвисать.

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

Недавно, кстати, в статье видел использование команды с принудительной перезагрузкой. Там автор наживую накатил на VPS поверх работающей системы RouterOS. Соответственно, текущую файловую систему он уничтожил, никакой бинарник запустить невозможно. А само ядро ОС всё ещё живёт в памяти и работает. Вот ему и можно отправить напрямую команду на перезагрузку.

Эта команда является частью так называемых Linux Magic System Request Key Hacks (sysrq). Магические сочетания клавиш, которые отправляют команды напрямую в ядро. Они реально привязаны к сочетаниям клавиш, выполняемых с управляющего терминала и подключенной клавиатуры. ALT + SysRq + <command key>. Клавиша SysRq часто совмещена с PrtSc. Уже не помню, когда последний раз сидел за экраном реального сервера, если это не мои домашние тестовые компы. Обычно везде хоть какой-то IPMI есть.

Ядро должно поддерживать эти команды. Обычно в популярных дистрибутивах это так:

# cat /proc/sys/kernel/sysrq

◽️ 0 - sysrq отключен
◽️ 1 - sysrq полностью включен
◽️ >1 - включены отдельные функции

На Debian или Centos, с которыми я больше всего работал, перезагрузка всегда срабатывала.

Команд, которые можно отправить ядру, довольно много. Я лично использую только b для перезагрузки. Остальные не помню и никогда не использовал. А про reboot помню. Видел рекомендации, что перед перезагрузкой попробовать какие-то другие команды, типа тех, что отмонтируют диски, завершат процессы и т.д. Обычно если ты жёстко ресетишь сервер, то пробовать что-то не имеет большого смысла, потому что уже висим.

Если всё же интересно, то весь список команд можно запросить у ядра:

# echo h > /proc/sysrq-trigger | less /var/log/kern.log

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #terminal
Каждый практикующий линуксоид хотя бы раз в жизни сталкивался с OOM Killer, который просто приходит и грохает какое-нибудь приложение. Чаще всего от этого страдают СУБД, так как они обычно самые жирные по потреблению памяти.

Небольшая инструкция на тему того, что делать, если на сервере кончается память и к вам приходит OOM Killer.

1️⃣ Первым делом я бы проверил системные логи на тему работы OOM Killer. Если у вас включены текстовые логи syslog, то сделать это проще всего так:

# grep -i Killed /var/log/syslog

Если текстовых логов нет, не знаю, как быстро посмотреть. Я всегда включаю текстовые логи. Надо запускать journalctl и там через поиск искать то же самое. Я всегда забываю горячие клавиши, которые управляют результатами поиска, поэтому предпочитаю текстовые логи.

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

2️⃣ Запускаем батю-скрипт на bash, который построит красивую табличку по приоритетным целям для OOM Killer:

printf 'PID\tOOM Score\tOOM Adj\tCommand\n'
while read -r pid comm; do [ -f /proc/$pid/oom_score ] && [ $(cat /proc/$pid/oom_score) != 0 ] && printf '%d\t%d\t\t%d\t%s\n' "$pid" "$(cat /proc/$pid/oom_score)" "$(cat /proc/$pid/oom_score_adj)" "$comm"; done < <(ps -e -o pid= -o comm=) | sort -k 2nr


Этот скрипт гуляет по комментариям и статьям. Я как-то заморочился и вроде бы нашёл автора, но не уверен, что это именно он. Однострочник только выглядит страшно. Если его записать с форматированием, то там простая структура. Её удобно взять за основу для формирования любых табличек с использованием ps и различных метрик. Может заморочусь и сделаю подборку из прикладных вещей, типа потребления памяти, сетевых соединений и т.д.

3️⃣ Теперь мы знаем, кого прибивает наш киллер, и видим в табличке OOM Score и OOM Adjustment. Чем выше первое значение, тем больше шансов, что процесс будет прибит. Если стоит 0, то не будет прибит никогда. Кто-то может подумать, что хорошо бы сделать нужному процессу Score 0, но это плохая идея. Если процесс течёт по памяти, то тупо виртуалка зависнет. Обычно так не делают. Второе значение - поправочный коэффициент для управления Score. Чем ниже этот коэффициент, в том числе с минусовыми значениями, тем меньше шансов, что OOM Killer убьёт нужный процесс.

Система этих очков и коэффициентов замороченная. Большого смысла в ней разбираться нет. Главное выставить приоритеты так, чтобы нужный вам процесс имел приоритет на убийство ниже остальных.

4️⃣ Прежде чем менять коэффициенты, идём в свои приложения и настраиваем в них потребление памяти, чтобы она на сервере не кончалась. Настраиваем мониторинг, если его нет. Чаще всего этого будет достаточно и трогать параметры OOM Killer не придётся.

5️⃣ Если используемые вами приложения не имеют своих настроек по потреблению памяти, то настроить их и поведение OOM Killer можно с помощью Systemd. У меня была отдельная заметка по этой теме. Там ничего сложного.

6️⃣ Когда всё настроили и хотите посмотреть, как себя поведёт система, если вдруг памяти не останется, то займите её всю чем-нибудь. Например, утилитой stress. Или просто в консоли запустите:

# python3 -c 'a="a"*1073741824; input()'

Заняли 1GB памяти. Подберите своё значение, чтобы памяти не осталось (2147483648 - 2GB, 3221225472 - 3GB и т.д.). После этого можно воспользоваться магической командой, про одну из которых я недавно писал:

# echo f > /proc/sysrq-trigger

Она принудительно вызывает OOM Killer. Пример, конечно, так себе, потому что OOM Killer скорее всего грохнет запущенную команду (хотя в моих тестах первым умер systemd). Чтобы этого избежать, надо дать ей низкий Score:

# echo -16 > /proc/$(pgrep python3)/oom_adj

Ещё раз вызываем киллера и смотрим, кого он прибьёт:

# echo f > /proc/sysrq-trigger
# grep -i Killed /var/log/syslog

У меня systemd умер первым.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#terminal #linux
Есть общая рекомендация по использованию дисков в Linuxсначала создать раздел на диске, а потом использовать его по назначению. Даже если у вас будет один раздел на весь диск, сделайте его. То есть использовать не /dev/sdb, а сделать на нём раздел, например с помощью cfdisk /dev/sdb, а потом уже использовать /dev/sdb1.

Какой-то одной явной причины делать именно так нет, и чаще всего всё будет в порядке даже без разделов, но в некоторых ситуациях могут возникать проблемы. Я опишу некоторые из них.

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

Ещё один случай от подписчика. У него коллега всегда использовал, как в текущей рекомендации, разделы. Как-то раз на сервере, где не им был добавлен в работу и использовался новый диск без разделов, он его по ошибке отредактировал, так как добавив другой новый диск ожидал именно его увидеть пустым, без разделов. По факту он ошибся, но если бы работающие диски были с разделами, этой ошибки бы не возникло.

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

В стародавние времена утилиты lsblk и blkid некорректно показывали информацию об идентификаторах, типах файловой системы на дисках без разделов.

Вся эта история тянется из прошлого. Как я уже сказал, сейчас возможно проблем и не будет, но тем не менее, лучше перестраховываться и создавать разделы. Я сам одно время не парился и если использовался весь диск, раздел не создавал. Потом узнал эту информацию и стал перестраховываться. Всегда создаю разделы, просто на всякий случай.

#совет #linux
Небольшой практический совет во время отладки в консоли Linux. Иногда хочется узнать, в каком окружении работает то или иное приложение. Поти вся информация о процессах в Linux живёт в /proc/<pid>, в том числе и об его окружении. Посмотреть можно так:

# cat /proc/816/environ

LANG=en_US.UTF-8PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/binHOME=/var/lib/zabbixLOGNAME=zabbixUSER=zabbixSHELL=/sbin/nologinCONFFILE=/etc/zabbix/zabbix_agentd.conf

Всё в одну строчку. Не воспринимается глазами вообще. Можно ещё вот так посмотреть:

# ps e -ww -p 816

Тоже не очень наглядно. Так как у нас консоль и bash, то вывод можно как угодно обрабатывать, чтобы было удобно. Проще всего взять xargs, так как у него есть ключ --null, который позволяет разделять строку, используя разделителем так называемый NULL character. Я уже как-то раз писал про него. Иногда его удобно использовать, в том числе в find с ключом -print0.

# cat /proc/816/environ | xargs --null --max-args=1

или то же самое, но немного по-другому:

# xargs --null --max-args=1 echo < /proc/816/environ
LANG=en_US.UTF-8
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
HOME=/var/lib/zabbix
LOGNAME=zabbix
USER=zabbix
SHELL=/sbin/nologin
CONFFILE=/etc/zabbix/zabbix_agentd.conf

Я уже болен cat-офилией и привык везде её использовать. Уже даже не пытаюсь переучиться. Вместо grep постоянно делаю cat | grep. Вы выбирайте, что вам легче запоминается.

На выходе получаем аккуратный список окружения процесса, где можно увидеть нужные нам нюансы быстрее и нагляднее, чем где-то в другом месте. И запоминать особо не надо, конструкция несложная. Главное ключ --null запомнить.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #bash
В стандартном репозитории Debian живёт неприметная и не особо популярная программа sosreport. Создана она была, судя по названию, для служб технической поддержки. Тем не менее, полезна может быть не только им. Она создаёт архив со слепком состояния системы. Этот архив включает в себя практически всю информацию о системе:

◽️Настройки Grub
◽️Все конфигурационные файлы из раздела /etc
◽️Информация о ядре, модулях, настройках sysctl
◽️Объекты systemd
◽️Различная информация о системе: версия, точки монтирования, информация о железе, кроны, пользователи, настройки сети, установленные пакеты и т.д.
◽️Информация о пользователях, история логинов, параметры.
◽️Логи из /var/log и journalctl
◽️И многое другое, функциональность расширяется плагинами, которые можно писать самостоятельно

По сути собрана вся доступная подробная информация о системе. Ставится так:

# apt install sosreport

Использовать удобнее всего так:

# sos report --batch --all-logs

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

Архив будет иметь имя вида sosreport-337737-2025-04-15-acgbmpx.tar.xz. Его можно распаковать и смотреть прямо тут, либо передать куда-то в другое место, распаковать и запустить сгенерированную html страничку sos.html, которая лежит в директории sos_reports.

Довольно удобная штука, чтобы быстро снять слепок состояния системы и потом спокойно его изучать, не боясь, что пока ты что-то ищешь или смотришь, состояние изменится. Так же предполагаю, что может быть полезно, например, раз в сутки делать такой слепок и складывать куда-то на некоторое время, просто на всякий случай. Архив получается маленький, проблем его хранить нет. Но в случае внештатной ситуации может помочь.

Ещё вариант применения - запускать по каким-то событиям мониторинга. Например, сработал триггер на загрузку процессора. Можно запустить скрипт с sosreport, который применит только плагин process и соберёт всю информацию о процессах.

# /usr/bin/sosreport --batch -o process

Sosreport выполнит и сохранит вывод следующих команд:

# ps auxwww
# lsof -b +M -n -l -c ''
# ps auxwwwm
# ps alxwww
# ps -elfL
# ps axo pid,ppid,user,group,lwp,nlwp,start_time,comm,cgroup
# ps axo flags,state,uid,pid,ppid,pgid,sid,cls,pri,addr,sz,wchan:20,lstart,tty,time,cmd

Можно и самому всё это выполнить и вывести куда-то, но через sosreport удобнее. Он к тому же может сразу положить архив куда-то по ftp или sftp с помощью ключей --upload, --upload-url, --upload-user, --upload-pass.

Я нечто подобное делала вручную и до сих пор использую. Описывал в своей статье:

Мониторинг списка запущенных процессов в Zabbix

Я там сделал более костыльно, но зато вывод сразу в history закидываю, чтобы можно было список процессов прямо в веб интерфейсе Zabbix смотреть.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux #мониторинг
Я очень много лет использовал в Linux утилиту screen для того, чтобы в случае обрыва связи при подключении по SSH не завершалось выполнение запущенных интерактивных операций. Особенно это касается обновлений системы через apt или dnf. Типичная проблема, не считая банального обрыва связи, - подключился по VPN к серверу, запустил обновление, обновился софт для VPN, тебя отключило, обновление завершилось на середине процесса. Это может привести к проблемам (система не загрузилась из-за прерванного обновления).

В screen меня всегда раздражало то, что после открытия и сворачивания Midnight Commander по комбинации клавиш CTRL + o, очищался терминал и ты не видел то, что там было до этого. Частично помогает скрол окна SSH клиента, но это неудобно и всё равно часть информации пропадает, обрезается.

В tmux такой проблемы нет. Всё работает ожидаемо, можно разворачивать, сворачивать MC, содержимое терминала не очищается. В итоге у меня на половине серверов по старинке screen стоит, на другой - tmux. Я никакими дополнительными возможностями tmux и screen не пользуюсь, мне главное при обрыве соединения вернуться в свою сессию. В screen привык к горячим клавишам и ключам и переучиваться на tmux не хотелось, так как нет большого смысла.

Оказывается, внутри screen есть свой скролер терминала. Достаточно нажать CTRL + a и потом [, откроется скролинг, где клавиашми PgUp / PgDn можно мотать вверх и вниз и читать содержимое терминала, в том числе то, что там было до запуска MC.

Возможно кому-то эта заметка поможет. Жаль, что я раньше об этом не узнал, столько лет раздражала эта фигня, примерно так же, как лесенка в MC, пока не узнал, как от неё избавиться.

Если кто только выбирает, что использовать, screen или tmux, рекомендую последний. По основным возможностям там примерно одно и то же, у tmux даже их больше, а по удобству, очевидности стандартных настроек, tmux тоже выигрывает. Я уже привык к screen, не хочется переучиваться, так как ничего принципиально нового для себя не получу. У tmux до сих пор подсматриваю горячие клавиши и ключи. Для screen это уже давно в голове отложилось и на автомате выполняется.

Когда-то давно опрос делал по поводу screen и tmux, кто чем пользуется. Результат был примерно 50 / 50. Примерно равная популярность у этих утилит. Сейчас ещё Zellij прибавилась. Но не думаю, что она сильно популярна и не станет таковой, пока не приедет в базовые репы. Вы что предпочитаете из этой троицы?

#linux #terminal
В Debian есть интересная библиотека libeatmydata, которая подменяет системные вызовы fsync, fdatasync, sync и некоторые другие на пустышки. Эти команды сразу выдают положительный результат, ничего не делая. То есть не работает подтверждение записи на диск.

Это существенно ускоряет все операции записи, но и, что логично, создаёт вероятность потери данных, так как реально они залетают в кэш, а не на диск. И будут записаны в зависимости от настроек и параметров системы, когда ядро посчитает нужным выполнить синхронизацию: по таймеру фоновой синхронизации или недостатка свободной оперативной памяти.

Работает это примерно так:

int fsync(int fd) {
return 0;
}


Реально там ещё пару проверок с if, но по сути всё так и есть для всех системных вызовов, что она она перехватывает.

Эту возможность без особых опасений можно использовать во временных или тестовых средах, где не важна сохранность данных. Причём сделать это очень просто. Ставим пакет:

# apt install eatmydata

Запускаем через него любую команду. Я протестировал на старой виртуалке, которую давно не обновляли. Сделал запуск обновления без eatmydata и с ней. Разница получилась заметной.

Напомню, что реальной установкой пакетов занимается утилита dpkg, а не apt. Dpkg для надёжности выполняет все действия с подтверждением записи. Так что если запустить её через eatmydata, она отработает гораздо быстрее.

Я выполнил полное обновление пакетов в два этапа, откатив первое обновление на изначальный снепшот:

# time apt upgrade -y
Fetched 249 MB in 30s (8,183 kB/s)
real 1m 43.690s

# time eatmydata apt upgrade -y
Fetched 249 MB in 33s (7,671 kB/s)
real 1m 36.984s

Работа dpkg занимает где-то треть всего времени, ещё треть загрузка пакетов, и треть пересборка initramfs. Без eatmydata dpkg работала примерно 30 секунд, с ней – 20.

Или вот ещё более наглядный тест. Запускаем создание файла в режиме синхронизации и подтверждения записи каждого блока:

# dd if=/dev/zero of=/mnt/tempfile bs=1M count=512 oflag=dsync
536870912 bytes (537 MB, 512 MiB) copied, 1.95211 s, 275 MB/s

И то же самое через eatmydata:

# eatmydata dd if=/dev/zero of=/mnt/tempfile bs=1M count=512 oflag=dsync
536870912 bytes (537 MB, 512 MiB) copied, 0.343773 s, 1.6 GB/s

Эта возможность может пригодиться при сборке контейнеров, образов, раскатки тестовых сред. Можно запускать тестовую СУБД через eatmydata. Да всё, что угодно на тестовом сервере.

Если у вас есть какие-то скрипты, которые не хочется переделывать, добавляя в начало каждой команды eatmydata, можете просто задать переменную окружения, в том числе глобальную в /etc/environment:

LD_PRELOAD=/usr/lib/x86_64-linux-gnu/libeatmydata.so

И все процессы будут писать без подтверждения записи в кэш.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux
Настраивал на днях арендованный сервер без прямого доступа к консоли. Ещё и конфигурация была нестандартная, так что техподдержка вручную установила туда ОС и отдала мне с доступом по SSH. Нужно было настроить дополнительные диски и добавить их в fstab. Несмотря на то, что в современных ОС реально монтирует диски systemd, я по старинке предпочитаю добавлять новые точки монтирования в fstab.

В этом деле самое главное – не ошибиться и сразу после изменения файла проверить, что там всё в порядке. Иначе после перезагрузки можно получить проблемы. Без прямого доступа к консоли это может быть фатально.

Я обычно добавляю новые диски в систему следующим образом. Смотрю список дисков через fstab:

# fdisk -l | grep /dev/

Сразу видно диски без разметки. Добавлять разделы предпочитаю в cfdisk, а не напрямую в консоли через fstab. В TUI как-то нагляднее, меньше шансов ошибиться.

# cfdisk /dev/sdb

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

# mkfs -t ext4 /dev/sdb1

Монтирую в систему:

# mkdir /mnt/disk1
# mount /dev/sdb1 /mnt/disk1

Теперь нам надо добавить эту точку монтирования в fstab. По имени диска категорически нельзя добавлять. Диски могут менять свои имена. Причём это стало актуально в какой-то момент с очередным обновлением железа. Когда я только начинал изучать Linux, спокойно монтировал по именам дисков и проблем не было. В какой-то момент они начались. И сейчас я сам часто наблюдаю, что диски, как и сетевые интерфейсы, могут изменить свои имена после перезагрузки. Если используете LVM, то можно добавлять точки монтирования по имени LV.

Смотрим UUID раздела:

# blkid | grep /dev/sdb1

Добавляем его в fstab отдельной строкой:

UUID=eaf5c153-08b7-4ea8-8037-e6baad4cac0d /mnt/disk1 ext4 errors=remount-ro 1 0

А теперь проверяем, всё ли мы правильно добавили.

# findmnt --verify --verbose

Findmnt проверил все монтирования. В моём случае я получил предупреждение на /media/cdrom0.

[W] unreachable source: /dev/sr0: No such file or directory

Судя по всему систему ставили с какого-то диска, локального или сетевого, не знаю, но он остался в fstab. Делать ему там больше нечего, можно закомментировать строку с ним.

Более кратко можно получить информацию только об ошибках:

# findmnt -x

☝️Отдельно обращаю внимание на такой момент. До перехода управления к systemd было критически важно оставлять в fstab в конце файла переход на новую строку. Сейчас даже если этого не сделать, то проблем не будет. Всё нормально загрузится. Насколько я понимаю, это тянется из далёкого прошлого и POSIX-совместимой практики, когда файлы конфигурации заканчивались переходом на новую строку. Я лично до сих пор на всякий случай везде этой практики придерживаюсь.

Ещё один способ проверить корректность записей в fstab – использовать mount. Можно не монтировать вручную новый диск, а сразу добавить его в fstab. Потом запустить:

# mount -a -v

Утилита смонтирует все записи из файла, где не указан параметр noauto. Если вы всё верно добавили, то ошибок не увидите и получите смонтированным новый диск.

Расскажу, что будет, если, к примеру, ошибётесь с диском в fstab или он просто перестанет быть видим в системе. Я лично с этим не раз сталкивался. А однажды это привело к дальней дороге. Добавили наживую новый диск в сервер, я его добавил с ошибкой в fstab и не проверил. Сервер аварийно перезагрузился через полгода из-за обесточивания серверной. Возникли какие-то проблемы с доступом туда, ещё и сервер по неизвестной на тот момент мне причине не стартанул. Приехал туда ножками и увидел примерно то же самое, что вы видите на втором скрине.

Сразу понял, в чём дело, зашёл в режим обслуживания и поправил fstab. Так что внимательно относитесь к его настройке. Этой проблемы можно избежать, если использовать nofail в параметрах монтирования. Но с ним могут быть нюансы. Иногда лучше не загрузиться, если с разделом проблемы.

❗️Если заметка вам полезна, не забудьте 👍 и забрать в закладки.

#linux