SystemdDoctor
служба не работает частое ресурсы дескрипторы limitnofile

Too many open files в журнале службы

Сообщение Too many open files (номер 24, EMFILE) значит, что служба исчерпала свой предел открытых файловых дескрипторов. Под дескрипторы попадают не только файлы, но и сетевые соединения — поэтому предел первым достигают нагруженные серверы и службы с утечкой.

Что это значит

У службы под systemd предел задаётся в unit-файле параметром LimitNOFILE=, и настройки в /etc/security/limits.conf на неё не действуют: тот файл относится к входу пользователей в систему. Это первая причина, по которой «я же поднял лимит» не срабатывает.

Вероятные причины

По порядку: сверху то, что встречается чаще.

  1. Предел в unit-файле слишком мал для нагрузки

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

  2. Утечка дескрипторов в самой программе

    Программа открывает файлы или соединения и не закрывает их. Тогда любой предел исчерпается — просто через большее время. Признак: число дескрипторов растёт монотонно.

  3. Исчерпан общесистемный предел

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

  4. Мягкий предел не поднят до жёсткого

    Программа видит мягкий предел. Если в unit-файле задать только жёсткий, программа продолжит упираться в мягкий, пока сама его не повысит.

Диагностика

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

Сколько дескрипторов держит служба прямо сейчас. Сравнение с пределом сразу даёт ответ.

PID=$(systemctl show -p MainPID --value myapp.service); ls /proc/$PID/fd | wc -l

Действующие пределы именно у службы, а не у вашего сеанса.

systemctl show myapp.service -p LimitNOFILE -p LimitNOFILESoft

Три числа: занято, свободно из занятых, общий предел системы.

cat /proc/sys/fs/file-nr

Решение

Решение своё для каждой причины. Сначала определите, какая из них ваша, — иначе правки наложатся друг на друга.

1. Предел в unit-файле слишком мал для нагрузки
Почему происходит
Значение по умолчанию (обычно 1024 мягкий предел) рассчитано на скромные службы. Веб-сервер, база или прокси на тысячах соединений исчерпывают его быстро.
Как проверить
Посмотрите действующий предел и текущее использование.
systemctl show myapp.service -p LimitNOFILE -p LimitNOFILESoft
cat /proc/$(systemctl show -p MainPID --value myapp.service)/limits | grep -i "open files"
Как исправить
Поднимите предел в unit-файле через drop-in и перезапустите службу. Для веб-серверов и баз обычное значение — от 16384 до 65535.
sudo systemctl edit myapp.service   # [Service]\nLimitNOFILE=65535
sudo systemctl restart myapp.service
2. Утечка дескрипторов в самой программе
Почему происходит
Программа открывает файлы или соединения и не закрывает их. Тогда любой предел исчерпается — просто через большее время. Признак: число дескрипторов растёт монотонно.
Как проверить
Посмотрите, сколько дескрипторов держит процесс сейчас, и сравните через несколько минут.
PID=$(systemctl show -p MainPID --value myapp.service); ls /proc/$PID/fd | wc -l
sudo ls -l /proc/$PID/fd | awk "{print \$NF}" | sort | uniq -c | sort -rn | head
Как исправить
Разбирайтесь с программой: вторая команда показывает, какого рода дескрипторы копятся. Поднятие предела тут лишь отложит сбой.
3. Исчерпан общесистемный предел
Почему происходит
Кроме предела процесса есть общий предел системы. При его исчерпании начинают отказывать все службы сразу.
Как проверить
Сравните использованное с допустимым.
cat /proc/sys/fs/file-nr
sysctl fs.file-max
Как исправить
Поднимите fs.file-max через файл в /etc/sysctl.d и найдите службу, которая держит основную массу дескрипторов.
echo "fs.file-max = 2097152" | sudo tee /etc/sysctl.d/99-files.conf && sudo sysctl --system
4. Мягкий предел не поднят до жёсткого
Почему происходит
Программа видит мягкий предел. Если в unit-файле задать только жёсткий, программа продолжит упираться в мягкий, пока сама его не повысит.
Как проверить
Посмотрите оба значения.
systemctl show myapp.service -p LimitNOFILE -p LimitNOFILESoft
Как исправить
Задавайте предел одним числом — тогда мягкий и жёсткий совпадут, — либо явной парой: LimitNOFILE=65535:65535.

Пример вывода

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

● nginx.service - A high performance web server and a reverse proxy server
     Active: active (running) since Mon 2026-09-15 08:00:01 MSK; 6h ago

nginx[1120]: 2026/09/15 14:02:31 [crit] 1120#1120: accept4() failed (24: Too many open files)
nginx[1120]: 2026/09/15 14:02:31 [alert] 1120#1120: *8812 socket() failed (24: Too many open files)

Здесь служба продолжает работать, но отказывает клиентам. Такие сообщения стоит замечать до того, как она упадёт.

Связанные ошибки

Где встречается чаще всего

Источники

  • systemd.exec(5)
    LimitNOFILE= и его отношение к limits.conf.
    официальная документация, systemd 255
    сверено 15 сентября 2026
  • Воспроизведено на тестовой машине, systemd 255 (Ubuntu 24.04)
    Воспроизведено на unit с LimitNOFILE=64 под нагрузкой; счёт дескрипторов через /proc.
    собственная проверка, systemd 255
    сверено 15 сентября 2026