Re: nginx есть десятки гигабат памяти и сервер уходит в swap

Maxim Dounin mdounin на mdounin.ru
Вт Янв 11 21:28:36 UTC 2022


Hello!

On Tue, Jan 11, 2022 at 06:10:43PM +0300, Дугин Сергей wrote:

> Здравствуйте, Maxim.
> 
> Вы писали 11 января 2022 г., 16:09:07:
> 
> > Hello!
> 
> > On Tue, Jan 11, 2022 at 05:54:36AM +0300, Дугин Сергей wrote:
> 
> >> Здравствуйте, Maxim.
> >> 
> >> Вы писали 10 января 2022 г., 22:07:16:
> >> 
> >> > А что при этом в конфиге?  В частности, worker_connections и 
> >> > всевозможные буфера (client_header_buffer_size, 
> >> > large_client_header_buffers, client_body_buffer_size, 
> >> > proxy_buffer_size, proxy_buffers, output_buffers и так далее)?  
> >> > Если включён HTTP/2 - то ещё и http2_max_concurrent_streams.
> >> Эти параметры все по дефолту.
> >> HTTP/2 - нет
> >> http2_max_concurrent_streams - тоже нет
> >> 
> >> > Отдельно интересно нет ли в конфиге сторонних модулей.  А если 
> >> > есть, то воспроизводится ли проблема без них.
> >> Сторонних модулей нет и не ставил
> >> в папке /usr/lib64/nginx/modules/
> >> нет ничего
> 
> > [...]
> 
> >> > Судя по всему, растут те процессы, которые собственно занимаются 
> >> > обработкой соединений: на современных линуксах распределение 
> >> > соединений между рабочими процессами может быть сильно 
> >> > неравномерным, лечить проще всего включением accept_mutex'а 
> >> > (https://trac.nginx.org/nginx/ticket/2285).
> >> Сделал worker_processes auto;
> >> форкеров стало ровно столько сколько ядер и теперь все форкеры кушают примерно одинаково:
> >>  6310 root      20   0 4494660   3.3g   2456 S   0.0  2.6   0:01.82 nginx
> >> 15109 root      20   0 4494660   3.3g   2452 S   2.3  2.6   0:01.32 nginx
> >> 15133 root      20   0 4494660   3.3g   2444 S   0.3  2.6   0:00.89 nginx
> >>  6216 root      20   0 4494660   3.3g   2420 S   0.0  2.6   0:00.65 nginx
> >>  6267 root      20   0 4494660   3.3g   2412 S   0.0  2.6   0:00.99 nginx
> >> 15085 root      20   0 4494660   3.3g   2344 S   1.6  2.6   0:00.94 nginx
> >>  6297 root      20   0 4494660   3.3g   2336 S   0.0  2.6   0:01.53 nginx
> >> 15097 root      20   0 4494660   3.3g   2332 S   2.3  2.6   0:01.09 nginx
> >> 14858 root      20   0 4494660   3.3g   2256 S   0.0  2.6   0:00.40 nginx
> >> 15045 root      20   0 4494660   3.3g   2300 S   0.7  2.6   0:00.54 nginx
> >> 15026 root      20   0 4494660   3.3g   2288 S   0.7  2.6   0:00.55 nginx
> >> и так далее
> 
> > В смысле - после включения accept_mutex'а?
> 
> Сделал так:
> events {
>   accept_mutex on;
> }
> и так
> worker_processes auto;
> 
> потребление процессами вроде равномерно.
> 
> Но ночью сделал
> worker_processes 6;
> и было так:
>   PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND
>  9477 root      20   0  101.9g  86.7g   2172 S   1.0 69.0  82:54.87 nginx
>  9467 root      20   0 5078884 275248   2204 S   1.0  0.2   9:18.31 nginx
>  9472 root      20   0 3510260 267848   2176 S   3.9  0.2   5:51.72 nginx
>  9475 root      20   0 3510260 258752   2252 S   1.0  0.2   8:01.37 nginx
>  9463 root      20   0 3510260 257088   2240 S   1.3  0.2   6:41.24 nginx
>  9480 root      20   0 3510260 224516   2256 S   0.3  0.2   7:15.55 nginx
>  9750 root      20   0 3510256  20856   1104 S   0.0  0.0   0:20.91 nginx
> То есть 
> accept_mutex on не помогло при малом числе процессов, но возможно и при worker_processes auto так же будет на более длинном промежутке

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

> >> При запуске писало 1.7g, сейчас уже 3.3g
> >> то есть при запуске потребляет 48*1.1=81,6g памяти,
> >> а сейчас уже 158,4G и сервер уже очень бодро свапится. 
> >> 
> >> 
> >> > Почему растут - отдельный вопрос.  Для начала, наверное, стоит 
> >> > посмотреть, до какого размера процессы могут расти по памяти в 
> >> > соответствии с текущими настройками.  Грубая оценка максимального 
> >> > потребления памяти одним рабочим процессом - worker_connections * 
> >> > <сумма всех буферов>.  Если она не превышена - то вопрос, скорее, 
> >> > в настройках, не соответствующих имеющемуся объёму памяти.  Если 
> >> > превышена - то имеет смысл разбираться дальше.
> >> 
> >> worker_connections поставил по дефолту
> >> буфера тоже все по дефолту
> >> worker_processes сделал 6
> >> 
> >> перезапустил вижу по top такое:
> >> USER     PID   %CPU %MEM VSZ     RSS     TTY   STAT START   TIME COMMAND
> >> root     15962  4.3  2.6 4477008 3467940 ?     S    05:42   0:01 nginx: worker process
> >> root     15954  1.6  2.6 4477008 3467916 ?     S    05:42   0:00 nginx: worker process
> >> root     15972  1.4  2.6 4477008 3467876 ?     S    05:42   0:00 nginx: worker process
> >> root     15982  0.4  2.6 4477008 3467720 ?     S    05:42   0:00 nginx: worker process
> >> root     15993  0.2  2.6 4477008 3467588 ?     S    05:42   0:00 nginx: worker process
> >> root     44803 15.8  2.6 4477004 3467200 ?     Ss   05:39   0:30 nginx: master process /usr/sbin/nginx -c /etc/nginx/nginx.conf
> >> root     16005  0.1  2.6 4477008 3465784 ?     S    05:42   0:00 nginx: worker process
> >> 
> >> В итоге 6 процессов кушают 3467940*6 около 20 гиг памяти при старте.
> 
> > Занятно.  А можно посмотреть конфиг полностью?  В идеале - сразу 
> > вывод "nginx -T", но можно выкинуть/отфильтровать имена серверов и 
> > прочую приватную информацию.
> 
> сделал так
> nginx -T | grep -v "server_name\|include\|access_log\|error_log\|\/var\/www\/\|^#\|ssl_certificate" > nginx.conf.1.txt
> IP заменил так же. 
> 
> Если удобнее могу архивнуть папку /etc/nginx/ и скинуть на личную почту.

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

Из наименее интрузивного - проще всего включить логгирование 
подзапросов (https://nginx.org/r/log_subrequest) и посмотреть, что 
вылезет в логах (но в общем случае может быть непросто отличить 
обычные запросы от подзапросов).  Ну или просто выключить SSI и 
посмотреть, уйдёт ли проблема.

-- 
Maxim Dounin
http://mdounin.ru/



Подробная информация о списке рассылки nginx-ru