Управление процессами в Linux: ps, top, htop, kill
Как устроены процессы в Linux, чем отличаются их состояния, как смотреть на них через ps, top и htop, останавливать через kill и killall, менять приоритет через nice и renice и разбираться с зомби-процессами.
Что такое процесс и зачем администратору в нём разбираться
Процесс в Linux — это работающий экземпляр программы: у него есть собственный идентификатор PID, выделенная память, открытые файловые дескрипторы и место в таблице процессов ядра. Когда веб-сервер не отвечает, диск заполняется логами непонятно от чего, или сервер внезапно тормозит без видимой причины, первый шаг диагностики почти всегда один и тот же — посмотреть, какие процессы сейчас работают, что они делают и сколько ресурсов потребляют.
Каждый процесс в любой момент времени находится в одном из нескольких состояний, и понимание этих состояний резко ускоряет диагностику. Основные состояния: R (running или runnable — выполняется или готов к выполнению и ждёт своей очереди у планировщика), S (interruptible sleep — ожидает события, например ввода с клавиатуры или ответа сети, и может быть разбужен сигналом), D (uninterruptible sleep — ожидает операцию ввода-вывода, обычно дисковую, и не реагирует на сигналы, пока операция не завершится), Z (zombie — процесс завершился, но родитель ещё не забрал его код возврата) и T (stopped — процесс приостановлен, например сигналом SIGSTOP или из отладчика).
ps -eo pid,ppid,stat,cmd --sort=-pcpu | head -20
На практике администратор чаще всего сталкивается с тремя вопросами: какой процесс ест CPU или память, почему процесс не отвечает и как его корректно завершить, и что делать со странными записями вроде зомби в списке процессов. Эта статья разбирает набор инструментов для ответа на все три вопроса — от простого снимка ps до интерактивных top и htop, и от мягкого kill до жёсткого SIGKILL с пониманием, какой сигнал когда уместен.
ps: снимок состояния процессов в конкретный момент
ps (process status) выводит статичный снимок процессов на момент запуска команды, в отличие от top, обновляющегося в реальном времени. Это делает ps удобным для скриптов и для быстрого разового просмотра, а не для наблюдения за динамикой.
ps aux
ps -ef
ps -eo pid,user,%cpu,%mem,vsz,rss,stat,start,time,cmd
В выводе ps aux колонка %CPU показывает долю использования одного ядра процессора за последний интервал измерения, %MEM — долю занятой физической памяти относительно общего объёма RAM на сервере, VSZ — виртуальный размер процесса в килобайтах (включая память, которая зарезервирована, но физически ещё не выделена), а RSS (resident set size) — реально занятую физическую память, что обычно интереснее при поиске утечек памяти, чем VSZ.
Колонка STAT содержит буквенный код состояния процесса, разобранный в предыдущем разделе, иногда с дополнительными модификаторами: символ "+" означает, что процесс работает на переднем плане текущей терминальной сессии, "s" — что процесс является лидером сессии, а "<" — что процесс работает с повышенным приоритетом (отрицательным значением nice).
ps -eo pid,ppid,cmd --forest
Флаг --forest строит визуальное дерево процессов с отступами, показывающими иерархию порождения: это особенно полезно, когда нужно понять, какой родительский процесс запустил проблемный дочерний, например увидеть, что зависший php-fpm воркер был порождён именно master-процессом php-fpm, а не запущен вручную из случайной сессии.
top: интерактивный монитор в реальном времени
top обновляет список процессов с заданным интервалом (по умолчанию раз в несколько секунд) прямо в терминале и входит в базовую поставку практически любого дистрибутива, поэтому доступен на сервере сразу после установки без дополнительных пакетов.
top
top -o %CPU
top -u www-data
top -p 1234,5678
Верхняя часть экрана top содержит сводку по системе: uptime и среднюю загрузку (load average за 1, 5 и 15 минут), количество процессов в разных состояниях, распределение CPU по категориям (us — пользовательское время, sy — системное время ядра, id — простой, wa — ожидание ввода-вывода), а также использование оперативной памяти и swap. Строка wa особенно важна при диагностике: устойчиво высокое значение wa при невысоком us сигнализирует, что сервер упирается не в CPU, а в дисковую подсистему или сетевое хранилище.
Внутри работающего top можно менять представление интерактивными клавишами без перезапуска: клавиша P сортирует список по загрузке CPU, M — по использованию памяти, k открывает приглашение для отправки сигнала выбранному процессу по его PID, r — для изменения приоритета через renice, а клавиша 1 переключает отображение суммарной загрузки CPU на отдельные показатели по каждому ядру, что полезно на многоядерных серверах для поиска процессов, использующих только одно ядро.
Клавиша c переключает командную строку между коротким именем процесса и полной командой с аргументами — это часто нужно, чтобы отличить, например, один воркер PHP-FPM от другого по обрабатываемому пулу, или увидеть полный путь к запущенному скрипту вместо общего имени интерпретатора.
htop: более наглядная альтернатива для повседневной работы
htop решает часть неудобств top: цветные индикаторы загрузки отдельно по каждому ядру CPU и по памяти в верхней части экрана, возможность прокручивать список процессов не только вниз, но и вправо для длинных командных строк, и управление процессами через функциональные клавиши внизу экрана без запоминания текстовых команд.
apt install htop
htop
Верхние строки htop показывают отдельную полосу загрузки для каждого ядра CPU (в top это нужно включать отдельно клавишей 1), полосу использования памяти и swap с разбивкой по цветам, а также счётчик задач и load average. Список процессов внизу по умолчанию показывает дерево процессов сразу, без отдельного флага, что упрощает понимание иерархии родитель-потомок без запуска ps --forest отдельно.
Функциональные клавиши внизу экрана дают доступ к основным действиям без запоминания текстовых команд: F3 — поиск процесса по имени, F4 — фильтр списка по подстроке, F5 — переключение древовидного вида, F6 — выбор столбца для сортировки, F9 — отправка сигнала выделенному процессу с выбором конкретного сигнала из списка, а не только SIGTERM по умолчанию. Клавиша пробел позволяет отметить сразу несколько процессов галочкой и применить действие (например, kill) сразу ко всем отмеченным.
На серверах без графического окружения и без прав на установку дополнительных пакетов top остаётся доступным средством по умолчанию, но там, где htop уже установлен или может быть установлен, он ощутимо ускоряет повседневную диагностику именно за счёт наглядности — особенно для администраторов, которые работают с несколькими серверами в течение дня и не хотят каждый раз заново разбирать плотный текстовый вывод top.
Сортировка и фильтрация: кто именно ест CPU и память
Самый частый практический вопрос при жалобе "сервер тормозит" — какой конкретно процесс виноват. И top, и htop, и ps дают быстрый ответ, если знать, какую сортировку и фильтр применить.
ps aux --sort=-%cpu | head -10
ps aux --sort=-%mem | head -10
Знак минус перед именем поля в --sort задаёт сортировку по убыванию — без минуса ps отсортирует по возрастанию, и самые тяжёлые процессы окажутся в конце длинного списка, что неудобно при поиске проблемы. Для разового снимка этого обычно достаточно, тогда как top -o %CPU или клавиша P внутри уже запущенного top дают то же самое, но с постоянным обновлением.
Если проблема не в конкретном процессе, а в целом классе процессов — например, нужно понять суммарное потребление памяти всеми воркерами PHP-FPM — сортировка отдельных строк неудобна, и стоит агрегировать по имени процесса.
ps -eo comm,rss | awk '{a[$1]+=$2} END {for (i in a) print a[i]/1024" MB", i}' | sort -rn | head -15
Такая агрегация быстро показывает, что, например, все воркеры php-fpm суммарно занимают несколько гигабайт памяти, даже если каждый отдельный воркер выглядит безобидно на фоне остальных строк — это типичная причина нехватки памяти на серверах с большим количеством дочерних процессов от одного пула.
kill, killall, pkill и разница между сигналами
Команда kill, несмотря на название, по умолчанию не убивает процесс мгновенно и жёстко — она отправляет процессу сигнал, а процесс сам решает, как на него реагировать (если вообще способен реагировать). Разные сигналы несут разный смысл, и выбор правильного сигнала — часть корректного администрирования, а не формальность.
kill -TERM 1234
kill -HUP 1234
kill -9 1234
kill -l
SIGTERM (сигнал по умолчанию для kill без указания номера) — это просьба корректно завершиться: процесс может перехватить этот сигнал, закрыть открытые файлы, сохранить состояние и завершиться аккуратно. SIGHUP исторически сигнализировал о разрыве терминальной сессии, но многие демоны (например, nginx) переопределили его смысл на "перечитать конфигурацию без полной остановки", что удобно для применения новых настроек без разрыва уже установленных соединений. SIGKILL (номер 9) обрабатывается ядром напрямую, минуя сам процесс, — процесс не может его перехватить, отложить или проигнорировать, поэтому это последний аргумент, когда процесс не реагирует на вежливые сигналы.
Практическое правило: сначала пробовать SIGTERM и дать процессу несколько секунд на завершение, и только если он не отреагировал — переходить к SIGKILL. Немедленный SIGKILL рискует оставить незакрытые файлы, недописанные данные на диск или повреждённые временные файлы, тогда как SIGTERM даёт процессу шанс завершиться чисто.
killall nginx
pkill -f "artisan queue:work"
pkill -u deploy
killall отправляет сигнал всем процессам с точно совпадающим именем — удобно, когда нужно остановить сразу все воркеры одного приложения, но опасно на серверах с несколькими похожими сервисами, поскольку легко случайно затронуть не тот процесс с похожим именем. pkill гибче: -f ищет совпадение по всей командной строке, а не только по имени исполняемого файла, что позволяет точно нацелиться, например, на конкретный скрипт очереди задач, запущенный через интерпретатор, а не через отдельный бинарник, а -u ограничивает поиск процессами конкретного пользователя.
nice и renice: управление приоритетом выполнения
Планировщик Linux распределяет процессорное время между процессами не строго поровну, а с учётом их приоритета (niceness) — значения от -20 (наивысший приоритет, процесс получает CPU в первую очередь) до 19 (наименьший приоритет, процесс уступает CPU всем остальным). По умолчанию новые процессы запускаются с приоритетом 0.
nice -n 15 ./heavy_backup_script.sh
renice -n 10 -p 4521
renice -n -5 -p 4521
nice задаёт приоритет при запуске нового процесса и полезен для заведомо тяжёлых фоновых задач вроде архивации бэкапов или пересчёта индексов — такой процесс не будет забирать CPU у активных пользовательских запросов, если система в этот момент и без того загружена, но при простое системы всё равно получит доступный CPU полностью. renice меняет приоритет уже работающего процесса без его перезапуска, что удобно, когда обнаружилось, что уже запущенная тяжёлая задача мешает остальным сервисам прямо сейчас.
Понижать приоритет собственных фоновых задач (увеличивать значение nice) может обычный пользователь без специальных прав, а вот повышать приоритет (уменьшать значение, уходить в отрицательные числа) разрешено только суперпользователю — это защита от ситуации, когда обычный пользователь мог бы искусственно "выбить" себе CPU в ущерб остальным процессам системы.
Зомби и осиротевшие процессы: в чём разница и когда волноваться
Зомби-процесс (состояние Z в выводе ps) — это процесс, который уже завершил выполнение, но его запись всё ещё числится в таблице процессов ядра, потому что родительский процесс ещё не вызвал системный вызов wait() для получения кода завершения потомка. Зомби не потребляет CPU и практически не занимает память — это лишь строка в таблице процессов ядра, но таблица процессов конечна, и при накоплении тысяч зомби система рано или поздно упрётся в лимит PID.
ps aux | awk '$8=="Z" {print}'
ps -eo ppid,pid,stat,cmd | grep " Z "
Убить зомби напрямую невозможно — kill не действует на процесс, который уже завершился, потому что убивать физически нечего. Единственный правильный путь — найти PPID (идентификатор родителя) зомби и разобраться с самим родителем: если это плохо написанный демон, не вызывающий wait() за своими дочерними процессами, зомби будут накапливаться постоянно, и решение — исправить или перезапустить именно родительский процесс, после чего ядро автоматически заберёт все висящие зомби этого родителя.
Осиротевший процесс — принципиально другая ситуация: это ещё активно работающий процесс, чей родитель завершился раньше него. В Linux такой процесс не остаётся без родителя вовсе — ядро автоматически переусыновляет его, назначая новым родителем init (PID 1) или systemd, в зависимости от системы инициализации. Осиротевшие процессы — это нормальное и безопасное явление, не требующее вмешательства, в отличие от накапливающихся зомби, которые всегда сигнализируют об ошибке в родительском коде.
Практический сценарий: сервер тормозит, куда смотреть по порядку
При жалобе на то, что сервер "тормозит", полезен фиксированный порядок диагностики, а не хаотичный перебор команд. Сначала стоит открыть top или htop и посмотреть на общую картину: значения us, sy и wa в верхней части экрана сразу подскажут, упирается ли сервер в вычисления (высокий us), в системные вызовы ядра (высокий sy, часто из-за интенсивной работы с файлами или сетью) или в дисковую подсистему (высокий wa).
uptime
top -b -n 1 | head -15
iostat -x 1 3
Флаг -b у top переводит его в неинтерактивный (batch) режим с выводом в обычный текстовый поток — это удобно для логирования состояния сервера по cron или для передачи вывода в файл при диагностике постфактум, когда проблема уже прошла, но нужно понять, что происходило в конкретный момент по сохранённым снимкам.
Если общая загрузка CPU высокая, следующий шаг — отсортировать процессы по %CPU и посмотреть, один ли это процесс-виновник или множество однотипных процессов суммарно создают нагрузку (как в примере с воркерами PHP-FPM выше). Если высок именно wa, стоит проверить конкретные диски через iostat -x и посмотреть, какой раздел или устройство перегружено операциями ввода-вывода, а не полагаться только на данные о CPU.
Отдельная частая причина мнимого "торможения" — не сам процесс, а нехватка свободной памяти, при которой ядро начинает активно использовать swap: в этом случае даже лёгкие по CPU операции начинают выполняться заметно медленнее из-за постоянного обмена страницами памяти между RAM и диском. Столбец SWAP в top и общий раздел использования памяти в верхней части экрана дают быстрый ответ на этот вопрос ещё до того, как разбираться с конкретными процессами.
Итоги: инструменты диагностики процессов и когда какой применять
ps — инструмент для разового статичного снимка и для использования в скриптах, где нужен точный, предсказуемый и легко парсящийся вывод без интерактивности. top — универсальный инструмент реального времени, доступный практически везде без установки, достаточный для большинства ситуаций диагностики на сервере. htop — более удобная и наглядная альтернатива top для повседневной ручной работы там, где его можно установить.
kill, killall и pkill решают одну и ту же задачу — отправку сигнала процессу — но с разной точностью нацеливания: по PID напрямую, по точному имени или по маске командной строки и владельцу. Разница между SIGTERM и SIGKILL — это разница между просьбой корректно завершиться и принудительной остановкой ядром без участия самого процесса, и правильный порядок действий — сначала мягкий сигнал, жёсткий только при необходимости.
Зная состояния процессов (R, S, D, Z, T) и умея быстро сортировать список по CPU или памяти, администратор сокращает время диагностики любой жалобы на "сервер тормозит" с догадок до нескольких точных команд — и именно это, а не запоминание десятков флагов, является главной практической ценностью разобранных здесь инструментов.
Почему стоит выбрать нас
Быстрый запуск
Подберём конфигурацию и развернём проект в день обращения.
Надёжность
NVMe-диски, защита от DDoS и резервные копии по расписанию.
Поддержка 24/7
Дежурные инженеры на связи в любое время суток.
Настройка под ключ
Установим CMS, настроим веб-сервер, SSL и почту за вас.
Перенос без простоя
Аккуратно перенесём сайт и базу данных на новый сервер.
Прозрачные цены
Актуальные тарифы и честный подбор без навязывания.
Вопросы и ответы
Чем ps aux отличается от ps -ef?
Это два разных набора синтаксиса для одной и той же утилиты: aux — стиль BSD без дефиса, ef — стиль System V с дефисом, и они выводят частично разный набор столбцов. ps aux показывает %CPU и %MEM сразу в выводе, а ps -ef показывает PPID (идентификатор родительского процесса) и время запуска в более явном виде — на практике достаточно любого из вариантов, выбор чаще дело привычки конкретного администратора.
Почему kill -9 не всегда останавливает процесс?
Сигнал SIGKILL (номер 9) обрабатывается не самим процессом, а ядром, и процесс не может его перехватить или проигнорировать, поэтому на уровне пользовательского пространства он останавливается почти всегда. Исключение — процесс, застрявший в непрерываемом состоянии ожидания ввода-вывода (состояние D), например из-за зависшего сетевого хранилища: такой процесс не будет обработан планировщиком, пока не завершится операция ввода-вывода, и kill -9 будет ждать в очереди сигналов до этого момента.
Что делать с зомби-процессом, если kill его не убирает?
Зомби-процесс уже завершил выполнение и не потребляет CPU — kill на него не подействует, потому что убивать уже нечего. Единственный способ убрать запись зомби из таблицы процессов — заставить его родительский процесс вызвать wait() и забрать код завершения, а если родитель сам завис или написан с ошибкой, придётся перезапускать или завершать именно родительский процесс.
В чём разница между top и htop?
top входит в состав практически любого дистрибутива Linux по умолчанию и не требует установки, но имеет менее удобный текстовый интерфейс без цвета и без возможности управлять процессами мышью или стрелками так же наглядно. htop — более современная альтернатива с цветными индикаторами загрузки по каждому ядру CPU, деревом процессов и возможностью прокрутки списка вправо для длинных командных строк, но требует отдельной установки в большинстве дистрибутивов.
Как узнать, какой процесс занимает конкретный порт?
Проще всего командой ss -tulpn с фильтрацией по нужному порту либо командой lsof -i :PORT, которая напрямую покажет PID и имя процесса, слушающего указанный порт — это особенно полезно при ошибке "address already in use" при попытке запустить сервис.
Что означает высокое значение load average при низкой загрузке CPU?
Load average учитывает не только процессы, активно использующие CPU, но и процессы, ожидающие в очереди на диск (состояние D) — если сервер упирается в медленный диск или сетевое хранилище, load average может быть высоким при формально свободном CPU, и в такой ситуации стоит смотреть на wa (iowait) в top, а не только на общую загрузку процессора.
Безопасно ли менять приоритет системных процессов через renice?
Понижать приоритет (увеличивать значение nice) собственных процессов безопасно и обычно даже полезно для фоновых задач, но повышать приоритет системных процессов ядра или демонов вроде sshd без крайней необходимости не стоит — они уже настроены с приоритетами, подходящими для стабильной работы системы, и вмешательство может привести к непредсказуемым задержкам в других частях системы.
Почему сумма %CPU в top может превышать 100%?
Значение %CPU в top считается относительно одного ядра процессора, поэтому многопоточный процесс, использующий несколько ядер одновременно, вполне может показывать 150% или 380% — на сервере с четырьмя ядрами теоретический максимум для одного процесса составляет 400%, и это нормальное поведение, а не ошибка отображения.
Как оплачивать услуги?
Оплата помесячная, для облачных серверов доступна почасовая тарификация. Принимаются карты, банковские переводы и электронные кошельки.
Есть ли круглосуточная поддержка?
Да, дежурные инженеры на связи 24/7.
Выдаёте ли закрывающие документы?
Да, предоставим необходимые документы для оплаты.
Как оставить заявку?
Заполните форму на странице или нажмите «Заказать» — мы свяжемся и поможем с подбором.