Asterisk: Out of memory: unable to allocate channel structure — решение сбоя RAM
- В логах ядра или консоли Asterisk:
ERROR[...]: utils.c: Out of memory: unable to allocate channel structure. - Asterisk аварийно завершает работу с сигналом
SIGSEGVилиSIGABRT(падение демона). - Невозможность совершать новые вызовы (абоненты получают сигнал 'Занято' или сброс).
- Потребление процесса
asteriskнепрерывно растет в выводеtop/htopдо лимитов cgroup/RAM.
1. Проверка лимитов файловых дескрипторов и памяти в systemd
Создайте оверрайд для службы Asterisk systemctl edit asterisk:
[Service]
LimitNOFILE=1048576
LimitNPROC=524288
LimitMEMLOCK=infinity
LimitCORE=infinitysystemctl daemon-reload && systemctl restart asterisk2. Анализ внутреннего распределения памяти Asterisk
Выполните диагностические команды в Asterisk CLI:
asterisk -rx "memory show summary"
asterisk -rx "core show channels count"
asterisk -rx "core show taskprocessors"Если число каналов аномально высоко при отсутствии реальных звонков, завершите зависшие каналы:
asterisk -rx "channel request hangup all"3. Очистка и ротация зависших модулей CDR / CEL / Регистраций
Утечки часто вызваны переполнением очередей баз данных (ODBC / MySQL). Ограничьте размер пула в /etc/asterisk/res_odbc.conf:
[asterisk]
enabled => yes
dsn => asterisk-connector
max_connections => 20
limit => 204. Включение сборщика Core Dump для отладки утечек
В /etc/asterisk/asterisk.conf включите:
[options]
debug = 0
dumpcore = yes Частые вопросы (FAQ)
Почему Asterisk падает с Out of memory при наличии свободной RAM в ОС?
Служба может упираться в системные лимиты ulimit (LimitAS, LimitDATA) или лимиты памяти в systemd slice (MemoryMax), даже если на физическом сервере есть свободная память.
Что делать, если растет счетчик Taskprocessors?
Выполните 'core show taskprocessors'. Если очереди забиты (allocated > 10000), сервер перегружен транскодированием, частыми обращениями к медленной БД или дисковым вводом-выводом.
Как найти модуль, вызвавший утечку памяти?
Скомпилируйте Asterisk с поддержкой MALLOC_DEBUG через menuselect (Compiler Flags) и отслеживайте аллокации через команду 'memory show allocations'.
Как автоматически перезапускать Asterisk при критическом сбое?
В systemd unit файле /etc/systemd/system/asterisk.service укажите директивы: Restart=always и RestartSec=5s.