Ограничение среза душит службу
Ограничения ресурсов наследуются по дереву контрольных групп: предел среза сильнее предела службы. Поэтому поднятие значения у службы не помогает, если исчерпан срез — и это неочевидно, пока не посмотришь дерево.
Вероятные причины
По порядку: сверху то, что встречается чаще.
-
Исчерпан предел среза
Все службы среза делят его ограничение. Одна служба может съесть весь предел, и остальные пострадают.
-
Служба в чужом срезе
Параметр среза мог быть задан ошибочно, и служба попала туда, где ограничения не про неё.
-
Ограничения заданы на нескольких уровнях
Дерево может иметь несколько уровней срезов, и ограничение любого из них действует. Смотреть нужно всю цепочку.
Диагностика
Команды идут в том порядке, в котором их стоит выполнять: каждая следующая проверяет то, что осталось после предыдущей.
В каком срезе работает служба.
systemctl show myapp.service -p SliceПотребление по уровням дерева.
systemd-cgtop -1 --depth=3 | head -12Ограничения родительского среза.
systemctl show system.slice -p MemoryMax -p TasksMaxРешение
Решение своё для каждой причины. Сначала определите, какая из них ваша, — иначе правки наложатся друг на друга.
- Почему происходит
- Все службы среза делят его ограничение. Одна служба может съесть весь предел, и остальные пострадают.
- Как проверить
-
Посмотрите пределы службы и её среза.
systemctl show myapp.service -p Slice -p MemoryMax -p TasksMax systemctl show system.slice -p MemoryMax -p TasksMax
- Как исправить
- Поднимите предел среза или вынесите службу в собственный срез с отдельным ограничением.
- Почему происходит
- Параметр среза мог быть задан ошибочно, и служба попала туда, где ограничения не про неё.
- Как проверить
-
Посмотрите, в каком срезе служба.
systemctl show myapp.service -p Slice systemd-cgls --no-pager | grep -B3 myapp
- Как исправить
-
Укажите нужный срез параметром
Slice=или оставьте значение по умолчанию.
- Почему происходит
- Дерево может иметь несколько уровней срезов, и ограничение любого из них действует. Смотреть нужно всю цепочку.
- Как проверить
-
Посмотрите дерево и пределы по уровням.
systemd-cgls --no-pager | head -20 systemctl show myapp.slice -p MemoryMax 2>/dev/null
- Как исправить
- Проверяйте ограничения по всей цепочке от корня до службы: самое строгое и определяет поведение.
Пример вывода
Предел службы поднят, упор остаётся из-за среза. Пример показательный: он собран на тестовой машине специально для этой страницы, а не взят из чужого журнала.
$ systemctl show myapp.service -p MemoryMax
MemoryMax=4294967296
$ systemctl show myapp.slice -p MemoryMax
MemoryMax=1073741824
systemd[1]: myapp.service: A process of this unit has been killed by the OOM killer.
Связанные ошибки
- Failed with result 'oom-kill' Состояние oom-kill: процесс службы убит из-за нехватки памяти. Как понять, упёрлись в предел службы или в память машины.
- Too many tasks: упор в предел TasksMax Служба не может создать новый процесс: достигнут предел TasksMax. Где он задан и как поднять правильно.
- Служба замедляется при упоре в MemoryHigh Мягкий предел памяти не убивает, но тормозит. Как заметить давление памяти и отличить его от нехватки.
- status=219/CGROUP в systemd Код 219/CGROUP: не удалось создать или настроить контрольную группу службы. Причины на уровне системы и контейнеров.
- Cannot allocate memory в журнале службы Не удалось выделить память: предел службы, память машины, настройка overcommit, исчерпанные области отображения.
- Disk quota exceeded для службы Место на разделе есть, а запись отклоняется: исчерпана дисковая квота пользователя или группы.
- Docker и kubelet: несовпадение драйвера cgroup Драйвер контрольных групп Docker не совпадает с systemd: предупреждения, нестабильная работа контейнеров, проблемы с kubelet.
- Elasticsearch: max virtual memory areas vm.max_map_count is too low Elasticsearch отказывается стартовать из-за заниженного vm.max_map_count. Как поднять значение и закрепить его.
Источники
-
systemd.resource-control(5)
Наследование ограничений по дереву контрольных групп. -
Воспроизведено на тестовой машине, systemd 255 (Ubuntu 24.04)
Воспроизведено пределом среза ниже предела службы.