Перейти до вмісту
EuroVPSEuroVPS

Як діагностувати високе споживання пам’яті в Linux

FAQ EuroVPS

Оновлено 6 хв читання

Shared FAQ page chrome (breadcrumb, dates, read time, «Читати далі», enquiry block, category labels): see INDEX-AND-CHROME.md. Translate once.

Body

Як знайти, що споживає пам’ять на сервері Linux, і які параметри overcommit ядра цим керують.

Виявлення ситуації «Out of Memory».

Коли ви дивитеся, тиск на пам’ять може вже минути, тому спочатку перевірте журнал ядра на наявність OOM-завершень: ядро Linux керує пам’яттю сервера, завершуючи завдання чи процеси за певними критеріями, і звільняє пам’ять, яку займав завершений процес.

Для кожного процесу, завершеного ядром, створюється запис у журналі; журнали зазвичай містяться в /var/log/.

Наведеною нижче командою grep можна пошукати помилку out of memory в усіх файлах журналів у /var/log/.

grep -i -r 'out of memory' /var/log/
Mar 1 01:24:05 srv kernel: [3966348.114233] Out of memory: Kill process 48305 (php-cgi) score 21 or sacrifice child
Mar 1 01:24:08 srv kernel: [3966350.061954] Out of memory: Kill process 48318 (php-cgi) score 21 or sacrifice child

Поточне використання:

root@srv:~# free -m 
              total        used        free      shared  buff/cache   available
Mem:     1981         720         319         138         940         916
Swap:      524          84         440

Історію використання пам’яті за день можна отримати командою «sar».

root@server [~]# sar -r
Linux (server.example.com)       03/05/2019      _x86_64_        (2 CPU)
12:00:01 AM kbmemfree kbmemused  %memused kbbuffers  kbcached  kbcommit   %commit
12:10:01 AM   1672764   1407160     45.69    100356    749140   1618364     44.90
12:20:01 AM   1289208   1790716     58.14    106580   1130096   1599588     44.38
12:30:01 AM   1248100   1831824     59.48    109184   1144680   1621332     44.98
12:40:01 AM   1267972   1811952     58.83    111460   1155828   1604104     44.51
12:50:01 AM   1254556   1825368     59.27    113888   1159632   1599480     44.38
01:00:01 AM   1092296   1987628     64.53    116020   1164540   1802228     50.00
01:10:01 AM   1212168   1867756     60.64    118204   1169516   1633940     45.33
...
Average:    kbmemfree kbmemused  %memused kbbuffers  kbcached  kbcommit   %commit
Average:      1465222   1614702        52.43          179213    834889      1655342     45.93

Оновлення RAM є необхідним, якщо сервер показує стабільно високе використання пам’яті або середнє використання за день перевищує 90%, оскільки таке високе використання часом може вичерпати доступну вільну пам’ять на завантаженому сервері. На віртуальній машині тривалий тиск на пам’ять вирішується більшою кількістю RAM або виправленням застосунку, ніколи не swap.

Ще один зручний інструмент для виявлення процесів, що споживають пам’ять, це команда «top», яка дає змогу сортувати запущені процеси за використанням ресурсів.

root@server [~]# top -c
top - 18:41:45 up 109 days, 18:03,  5 users,  load average: 1.30, 1.24, 1.24
Tasks: 544 total,   2 running, 541 sleeping,   0 stopped,   1 zombie
Cpu(s):  8.3%us,  1.4%sy,  0.2%ni, 89.8%id,  0.3%wa,  0.0%hi,  0.1%si,  0.0%st
Mem:  12296096k total, 11531800k used,   764296k free,   586732k buffers
Swap: 16777212k total,   209160k used, 16568052k free,  2471072k cached
    PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND                                                                                                                    
2376001 root      20   0  230m 101m 4588 R 31.4  0.8   1:22.06 spamd child                                                                                                                 
2448741 root      30  10 19472 1056  792 S  2.6  0.0   0:00.08 /usr/sbin/lveps -c 1 -p -d -n -o id:10,ep:10,pno:10,pid:15,tno:5,tid:15,cpu:7,mem:15,com:256                                
 953572 mysql     20   0 17.5g 5.3g 5336 S  1.7 44.9 102:38.10 /usr/sbin/mysqld --basedir=/usr --datadir=/var/lib/mysql --plugin-dir=/usr/lib64/mysql/plugin --user=mysql --log-error=server
 844549 root      30  10  424m  59m 4532 S  1.3  0.5  52:13.20 /opt/alt/python27/bin/python2.7 /usr/share/lve-stats/lvestats-server.py start --pidfile /var/run/lvestats.pid               
1351883 root      20   0 1127m 638m 1768 S  1.3  5.3  37:37.24 /usr/local/cpanel/3rdparty/bin/clamd                                                                                        
 844526 root      30  10  462m  35m 1204 S  1.0  0.3  30:54.20 /opt/alt/python27/bin/python2.7 /usr/share/lve-stats/lvestats-server.py start --pidfile /var/run/lvestats.pid               
   3109 nscd      20   0 2725m 3956 2260 S  0.7  0.0 188:08.43 /usr/sbin/nscd                                                                                                              
2243573 nobody    20   0  189m  78m 1140 S  0.7  0.7   4:22.20 litespeed (lshttpd - #01)                                                                                                   
2448384 mailnull  20   0 78756 7736 3348 S  0.7  0.1   0:00.06 /usr/sbin/exim -bd -q1h -oP /var/spool/exim/exim-daemon.pid

Щоб відсортувати процеси за використанням пам’яті, скористайтеся такою послідовністю клавіш.

Введіть команду top. Натисніть SHIFT+o, щоб відкрити опції команди top. Натисніть N і Enter.

Виявлення витоків пам’яті

Можна знайти час сервера, коли було зафіксовано «out of memory»; тут це “Mar 1 01:24:05”. Пошукайте цю позначку часу командою grep у файлах журналів ваших серверів застосунків, таких як Apache, MySQL тощо.

На сервері cPanel командою grep можна пошукати в журналах доступу сайтів будь-який підозрілий або зловмисний доступ до сайту, який спричинив вичерпання ресурсів.

grep  -ir “01/Mar/2019:01:2”  /usr/local/apache/domlogs/

Деякі підозрілі дії, які видно в журналах доступу:

  1. Велика кількість звернень з конкретних IP-адрес.
  2. Велика кількість звернень до відсутніх ресурсів або файлів.
  3. Велика кількість запитів HTTP POST.
  4. Велика кількість невдалих спроб доступу, наприклад входу.

Командою mysqladmin proc stat можна виявити запити MySQL, які зависли надовго і через це споживають багато пам’яті.

root@server [~]# mysqladmin proc stat
+--------+------+-----------+----+---------+------+-------+------------------+----------+
| Id     | User | Host      | db | Command | Time | State | Info             | Progress |
+--------+------+-----------+----+---------+------+-------+------------------+----------+
| 137324 | root | localhost |    | Query   | 0    | init  | show processlist | 0.000    |
+--------+------+-----------+----+---------+------+-------+------------------+----------+
Uptime: 370827  Threads: 1  Questions: 20484133  Slow queries: 0  Opens: 1456  Flush tables: 1  Open tables: 747  Queries per second avg: 55.239

Перевірте стовпці Time, db, State, знайдіть запити з великим значенням «Time» і розгляньте їх разом із розробником вашого сайту.

Увімкніть «журнал повільних запитів» у MySQL і виправте довгі запити разом із розробником вашого сайту.

Memory Overcommit

Зазвичай сервер Linux дозволяє зарезервувати для процесу більше пам’яті, ніж йому фактично потрібно, виходячи з припущення, що жоден процес не використає всю дозволену йому пам’ять, яку можна віддати іншим процесам. Поведінку системи Linux щодо overcommit пам’яті можна налаштувати, і робиться це утилітою sysctl.

Усі параметри sysctl можна вивести командою sysctl -a; параметр, який нас цікавить, це vm.overcommit_memory.

[root@srv ~]# sysctl -a | grep vm.overcommit_memory
vm.overcommit_memory = 0

vm.overcommit_memory може мати 3 значення: 0, 1 і 2.

  • 0 Дозволяти overcommit за оцінкою «якщо RAM достатньо»
  • 1 Завжди дозволяти overcommit
  • 2 Відмовляти в overcommit, якщо в системі немає пам’яті.

Ще один параметр sysctl, який варто врахувати, це overcommit_ratio: він визначає, який відсоток фізичної пам’яті на додаток до простору swap можна враховувати, дозволяючи процесам overcommit.

Розгляньмо випадок, коли vm.overcommit_memory встановлено в 2: ядро не дозволить overcommit понад простір swap плюс vm.overcommit_ratio від загального обсягу RAM vm.overcommit_memory=2 vm.overcommit_ratio=50% RAM=8GB SWAP=4GB

За наведеної конфігурації overcommit можливий у межах 4GB SWAP + 50% від 8GB RAM

sysctl -w vm.overcommit_memory=2
sysctl -w vm.overcommit_ratio=100

sysctl -w не зберігається після перезавантаження; додайте ті самі два рядки до /etc/sysctl.conf.

З FAQ EuroVPS.

Більше в категорії «Інструкції»

Ваш наступний партнер з інфраструктури

Залишилося
запитання?

Розкажіть, що ви намагаєтеся зробити. Інженер прочитає і відповість.

+357 222 32280
Інженер EuroVPS несе серверний вузол у залі дата-центру
Розмова з людьми, які доглядатимуть за вашою інфраструктурою.

Почнімо з вашої інфраструктури.

Трохи контексту допомагає нам почати правильну розмову.

Ми використаємо ваші дані, щоб відповісти на ваш запит. Політика конфіденційності