Как приручить отзывчивость Linux, память и подкачку


27

Первый вопрос о переполнении =) ... +100 награда. Не мог придумать то, о чем я действительно заботился до сих пор:

Я действительно сыт по горло состоянием отзывчивости рабочего стола Linux, например, http://brainstorm.ubuntu.com/item/85/ - в ситуациях с нехваткой свободной оперативной памяти или в ситуациях с высокой пропускной способностью диска система замедляется до ползать ; это абсолютно ужасно для приложений, которые требуют приличной производительности. Кроме того, пользовательский интерфейс полностью не отвечает. Сравните это, например, с OS X, где, если приложение захватывает ресурсы, всегда можно щелкнуть по опции, чтобы принудительно завершить его, тогда как в Linux я не могу даже alt-tab или переключить рабочий стол, или даже ctrl-alt-f1, чтобы получить терминал - ну, я могу, это займет около 1-2 минут за операцию.

Я использую gkrellm, чтобы видеть ситуацию, когда она разворачивается. Обычно использование памяти становится довольно высоким, или пропускная способность диска резко возрастает.

Это неплохое аппаратное обеспечение, с четырехъядерным процессором 2,6 ГГц и 4 ГБ оперативной памяти DDR2 800 МГц (было бы 6 ГБ, но из-за несовместимости аппаратного обеспечения нельзя было совмещать и сравнивать со старым набором). Эта проблема может уйти, когда я неизбежно получу больше оперативной памяти, но я не чувствую, что это суть проблемы. У меня даже есть два раздела подкачки на разных дисках.

Я чувствую, что проблема тройная:

  • беглые программы, которые занимают огромные объемы памяти - для этих программ должен быть установлен закон с ограничениями на их использование.
    • (например, вкладки в Chrome, каждая из которых имеет размер 20-50 МБ, некоторые из которых могут использовать сотни МБ)
    • (например, другие программы, такие как update-db и indexers, которые мне пришлось отключить и удалить из cron, потому что они замедляли работу системы при каждом запуске и т. д.)
  • что-то ужасное, происходящее в ядре или конфликте шины какого-то рода, например, ситуации с высокой пропускной способностью диска замедляют работу всей системы (возможно, из-за подкачки важных программ)
  • ядро не назначает приоритеты пользовательскому интерфейсу или важным программам с точки зрения ресурсов, таких как память, пейджинг, даже загрузка процессора

Upvotes перейти к:

Таким образом, я ищу решение, где все такие программы уходят. В частности, я ищу решение, позволяющее пропорционально замедлять процессы, в то время как система и другие программы остаются совершенно незатронутыми и реагируют достаточно долго, чтобы что-то вручную убить. Кроме того, процесс оконного менеджера (и все остальное, что может повлиять на отзывчивость пользовательского интерфейса) должен быть отзывчивым при любых обстоятельствах.

В частности, я заинтригован /etc/security/limits.conf( man limits.conf), но я обеспокоен тем, что это дает только контроль за пользователем, и прокомментированные примеры в файле кажутся довольно непрозрачными с точки зрения описания или с чего начать. Я надеюсь, что это limits.confсработает, но я не удивлюсь, если это даже не сработает, или если это не будет подходящим решением для моей проблемы, или настолько гранулированным, насколько я пытаюсь достичь. Для каждого процесса limits.confбыло бы идеально использовать имя, если предположить, что limit.conf работает. Я был бы рад попробовать файл limit.conf, который предоставляют люди, чтобы проверить, работает ли он, хотя я открыт для всех решений на данный момент.

Также может быть полезно иметь представление о том, как OS X удается поддерживать такую ​​хорошую отзывчивость пользовательского интерфейса.

Я уже настроил мои /tmpпапки и папки кэша tmpfs, и в целом использование диска почти равно нулю.

Смутно связанные темы:

  • переполнение памяти

Не думаю, что ответы будут работать:

  • swapoff (это по-прежнему позволяет программам, занимающимся захватом памяти, избавляться от убийств, а система постоянно зависает, если память действительно плохая - приветствует любого, кто может предложить твик, который ранее вызывал OOM-killer перед заменой и предназначался для определенных программ)
  • echo ?? > /sys/.../swappiness (без заметного эффекта)
  • nice (никогда не работал)
  • ionice (никогда не замечал разницы)
  • selinux (несовместимость программ кажется кошмаром)
  • Linux реального времени, то есть может прерывать ядро ​​(не хочу иметь дело с компиляцией и обновлением собственного ядра; может быть, все в порядке, если оно перенесено в репозитории)
  • *

хм, кажется, я не могу назначить награду; Я думаю, что ссылка не отображается в течение 48 часов? ... хорошо, я буду публиковать награду со всей репутацией, которую я приобрел тогда
user76871

1
+1, это единственная самая большая проблема, с которой я сталкиваюсь с рабочим столом Linux в повседневной жизни. У меня случаются замерзания, возможно, раз в пару недель, но их не достаточно часто, чтобы раздражать. Тем не менее, это только кажется, что проблема с приложениями, которые, как вы сказали, интенсивно использует ввод-вывод : приложения с высокой загрузкой ЦП практически не влияют на общую производительность системы. Не знал об этом, кажется, что это будет правильным решением этой проблемы, если он будет работать должным образом.
crazy2be

1
3 года спустя, и это все еще проблема в Linux. @ crazy2be или user76871, я не думаю, что вы нашли решение в то же время?
Glutanimate

@Glutanimate: да, 32 ГБ физической ОЗУ и не меньше (ну, может быть, 16 ГБ ... но это подталкивает), а также большие объемы видеопамяти. Это не устраняет безответственность из-за высокой загрузки ЦП, прерываний или чего-то еще, но предотвращает безответственность в ситуациях с нехваткой памяти.
user76871

Ответы:


6

Звучит так, будто ваша система сильно обменивается. Использование vmstat 1может раскрыть некоторые детали - просто дайте ему запуститься в окне терминала и переключитесь на него, когда начнется замедление.

Вместо того, чтобы помещать / tmp и «cache» в tmpfs, я бы использовал обычную дисковую файловую систему, смонтированную с noatimeопцией. Часто используемые данные остаются в кэше в любом случае, а старые данные могут быть записаны на диск, чтобы освободить часть оперативной памяти для приложений. Если / tmp и / или кеш увеличивается, это может сильно помочь.


1
+1 за упоминание noatime.
LawrenceC

Спасибо, что упомянули noatime, к сожалению, я использовал эту опцию монтирования, и я не думаю, что она сильно помогла обеспечить отзывчивость (хотя это очень помогает гарантировать, что диск не перегружен); просто чтобы убедиться, что я снова включил noatime в моей текущей настройке. Иметь non-tmpfs с noatime кажется немного странным, так как я все еще представляю, что массивные записи должны произойти.
user76871

+1, попробовал vmstat 1- чрезвычайно полезен в диагностике кликов, что свопинг - это, по сути, большая часть проблемы
user76871

2
Уч. Никогда не видел системы Linux, которая требовала такой тяжелой замены. Вы проверили, df -mсколько памяти используется в файловых системах tmpfs? Что - то будет есть ваш RAM относительно быстро.
Турбо J

спасибо за предложение и обучение меня о -mвыборе. К сожалению, df -h -mкажется, указывает на то, что в моей памяти всего 100 МБ tmpfs, поэтому я сомневаюсь, что это связано с использованием памяти для tmpfs и кешей. Это также не кажется чем-то необычным; У меня было это на нескольких дистрибутивах, когда их ОЗУ приближается к пределу.
user76871

5

Я не разработчик ядра, но я потратил годы на то, чтобы философствовать по этому вопросу, потому что я сталкивался с таким много раз Я на самом деле придумал метафору для всей ситуации, поэтому позвольте мне сказать вам это. В своей истории я предполагаю, что таких вещей, как «своп», не существует. В наши дни своп не имеет особого смысла с 32 ГБ ОЗУ.

Представьте себе ваш район, где вода подключена к каждому зданию через трубы, и город должен управлять мощностью. Предположим, что вы производите только 100 единиц воды в секунду (и вся неиспользованная емкость уходит в отходы, потому что у вас нет резервуаров). Каждый дом (дом = маленькое приложение, терминал, виджет часов и т. Д.) Требует 1 единицу воды в секунду. Это все хорошо и хорошо, потому что вашему населению около 90 лет, поэтому все получают достаточно воды.

Теперь мэр (= вы) решите, что вы хотите открыть большой ресторан (= браузер). В этом ресторане будет несколько поваров (= вкладки браузера). Каждый повар нуждается в 1 единице воды в секунду. Вы начинаете с 10 поваров, поэтому общее потребление воды для всего района составляет 100 единиц воды, что все еще хорошо.

Теперь начинается самое интересное: вы нанимаете в свой ресторан еще одного повара, который предъявляет 101 потребность в воде, которой, очевидно, у вас нет. Вам нужно что-то сделать.

Управление водой (= ядро) имеет 3 варианта.

1. Первый вариант - просто отключить услугу для домов, которые недавно не пользовались водой. Это нормально, но если отключенный дом захочет снова использовать воду, им придется снова пройти длительный процесс регистрации. Управление может отключить несколько домов, чтобы высвободить больше водных ресурсов. На самом деле, они отключат все дома, в которых вода не использовалась в последнее время, таким образом, всегда будет доступно некоторое количество бесплатной воды.

Хотя ваш город продолжает функционировать, недостатком является то, что прогресс останавливается. Большая часть вашего времени тратится на ожидание управления водными ресурсами для восстановления вашего обслуживания.

Это то, что делает ядро ​​со страницами с файловой поддержкой. Если вы запускаете большой исполняемый файл (например, Chrome), его файл копируется в память. Если памяти мало или есть части, к которым недавно не обращались, ядро ​​может отбросить эти части, потому что оно в любом случае может перезагрузить их с диска. Если это делается чрезмерно, это останавливает ваш рабочий стол, потому что все будет просто ждать дискового ввода-вывода. Обратите внимание, что ядро ​​также удалит много наименее недавно использованных страниц, когда вы начнете делать много операций ввода-вывода. Вот почему требуются годы, чтобы переключиться на фоновое приложение после того, как вы скопировали несколько больших файлов, таких как образы DVD.

Это самое раздражающее поведение для меня, потому что я ненавижу хип-хопы, а ты не можешь их контролировать. Было бы неплохо иметь возможность выключить его. Я думаю о чем-то вроде

sed -i 's/may_unmap = 1/may_unmap = (vm_swappiness >= 0)/' mm/vmscan.c

и затем вы можете установить vm_swappiness в -1, чтобы отключить это. Это работало довольно хорошо в моих маленьких тестах, но, увы, я не разработчик ядра, поэтому я никому не отправлял (и, очевидно, небольшая модификация выше не завершена).

2.Руководство может отклонить просьбу нового повара о воде. Это изначально звучит как хорошая идея. Однако есть два недостатка. Во-первых, есть компании, которые запрашивают много подписок на воду, хотя и не пользуются ими. Одна из возможных причин сделать это - избегать лишних разговоров с руководством по водоснабжению, когда им требуется дополнительная вода. Их использование воды идет вверх и вниз в зависимости от времени дня. Например, в случае с рестораном компании нужно гораздо больше воды в полдень по сравнению с полуночью. Таким образом, они просят всю возможную воду, которую они могли бы использовать, но это напрасно расходует воду в течение полуночи. Проблема в том, что не все компании могут правильно предвидеть свое пиковое использование, поэтому они запрашивают намного больше в надежде, что им никогда не придется беспокоиться о запросе большего.

Это то, что делает виртуальная машина Java: она выделяет кучу памяти при запуске, а затем работает из этого. По умолчанию ядро ​​выделяет память только тогда, когда ваше Java-приложение фактически начинает ее использовать. Однако, если вы отключите overcommit, ядро ​​будет серьезно относиться к резервированию. Это только позволит распределению быть успешным, если у него действительно есть ресурсы для этого.

Однако есть еще одна, более серьезная проблема с этим подходом. Допустим, одна компания начинает запрашивать одну единицу воды каждый день (а не с шагом 10). В конце концов вы достигнете состояния, в котором у вас есть 0 бесплатных юнитов. Теперь эта компания не сможет выделять больше. Это хорошо, кто заботится о больших компаниях так или иначе. Но проблема в том, что небольшие дома также не смогут запрашивать больше воды! Вы не сможете построить небольшие общественные ванные комнаты, чтобы справиться с внезапным наплывом туристов. Вы не сможете обеспечить аварийную воду для огня в соседнем лесу.

С точки зрения компьютера: в ситуациях с нехваткой памяти без чрезмерной загрузки вы не сможете открыть новый xterm, вы не сможете подключиться к своей машине по ssh, вы не сможете открыть новую вкладку для поиска возможных исправления. Другими словами, отключение overcommit также делает ваш рабочий стол бесполезным, когда мало памяти.

3. Теперь вот интересный способ решения проблемы, когда компания начинает использовать слишком много воды. Управление водными ресурсами взрывает это! Буквально: он идет на сайт ресторана, бросает в него динамиты и ждет, пока он не взорвется. Это мгновенно сократит потребности города в воде, так что новые люди могут переехать, вы можете создать общественные ванные комнаты и т. Д. Вы, как мэр, можете перестроить ресторан в надежде, что на этот раз потребуется меньше воды. Например, вы скажете людям не ходить в рестораны, если внутри уже слишком много людей (например, вы откроете меньше вкладок браузера).

Это действительно то, что делает ядро, когда у него заканчиваются все параметры и ему требуется память: оно вызывает убийцу OOM. Он выбирает большое приложение (основанное на множестве эвристик) и убивает его, освобождая кучу памяти, но поддерживая отзывчивый рабочий стол. На самом деле ядро ​​Android делает это еще более агрессивно: оно убивает наименее используемое приложение, когда памяти мало (по сравнению со стандартным ядром, которое делает это только в крайнем случае). Это называется убийцей викингов в Android.

Я думаю, что это одно из самых простых решений проблемы: у вас не так много вариантов, как это, так почему бы не преодолеть это раньше, чем позже, верно? Проблема в том, что ядро ​​иногда выполняет довольно много работы, чтобы избежать вызова OOM killer. Вот почему вы видите, что ваш рабочий стол очень медленный, и ядро ​​ничего не делает с этим. Но, к счастью, есть возможность вызвать убийцу ООМ самостоятельно! Сначала убедитесь, что магический ключ sysrq включен (например echo 1 | sudo tee /proc/sys/kernel/sysrq), а затем, когда вы чувствуете, что ядру не хватает памяти, просто нажмите Alt + SysRQ, Alt + f.

Хорошо, так что все это хорошо, но вы хотите попробовать? Ситуация с низкой памятью очень просто воспроизвести. У меня есть очень простое приложение для этого. Вам нужно будет запустить его дважды. Первый запуск определит, сколько свободной оперативной памяти у вас есть, второй запуск создаст ситуацию с нехваткой памяти. Обратите внимание, что этот метод предполагает, что у вас отключен своп (например, сделайте a sudo swapoff -a). Код и использование следующим образом:

// gcc -std=c99 -Wall -Wextra -Werror -g -o eatmem eatmem.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

int main(int argc, char** argv)
{
    int limit = 123456789;
    if (argc >= 2) {
        limit = atoi(argv[1]);
    }
    setbuf(stdout, NULL);
    for (int i = 1; i <= limit; i++) {
        memset(malloc(1 << 20), 1, 1 << 20);
        printf("\rAllocated %5d MiB.", i);
    }
    sleep(10000);
    return 0;
}

А вот как вы это используете:

$ gcc -std=c99 -Wall -Wextra -Werror -g -o eatmem eatmem.c
$ ./eatmem
Allocated 31118 MiB.Killed
$ ./eatmem 31110
Allocated 31110 MiB.Killed

Первый вызов обнаружил, что у нас есть 31 118 МБ свободной оперативной памяти. Поэтому я сказал приложению выделить 31 110 МБ ОЗУ, чтобы ядро ​​не убивало его, а почти полностью поглощало мою память. Моя система зависла: даже указатель мыши не сдвинулся с места. Я нажал Alt + SysRQ, Alt + f, и это убило мой процесс eatmem, и система была восстановлена.

Несмотря на то, что мы рассмотрели наши варианты действий в ситуации с нехваткой памяти, лучший подход (как и в любой другой опасной ситуации) - это в первую очередь избегать этого. Есть много способов сделать это. Один из распространенных способов, которые я видел, - помещать неправильно работающие приложения (например, браузеры) в другие контейнеры, чем остальная часть системы. В этом случае браузер не сможет повлиять на ваш рабочий стол. Но сама профилактика выходит за рамки вопроса, поэтому я не буду об этом писать.

TL; DR: хотя в настоящее время нет способа полностью избежать подкачки страниц, вы можете уменьшить полную остановку системы, отключив overcommit. Но ваша система все еще будет неработоспособна в ситуации нехватки памяти, но другим способом. Независимо от вышесказанного, в ситуации нехватки памяти нажмите Alt + SysRQ, Alt + f, чтобы убить большой процесс выбора ядра. Ваша система должна восстановить свою отзывчивость через несколько секунд. Предполагается, что у вас включен магический ключ sysrq (по умолчанию это не так).


Я дал вам всю свою репутацию в качестве награды за этот ресурс, поэтому я даже не мог оставить комментарий :) Наконец, я заработал несколько слов, чтобы поблагодарить вас за этот отличный ответ! Я имел дело с этой проблемой все время, когда у меня был ноутбук с 8 ГБ (сумасшедший, но моя система регулярно выходила из памяти в те дни). Недавно я нашел этот проект: github.com/rfjakob/earlyoom , который может помочь предотвратить зависание системы, убив некоторые процессы, пока не стало слишком поздно.
Влад Фролов

4

Размещение всех ваших временных файлов и файлов кэша tmpfsснижает объем свободной оперативной памяти, которая у вас есть, поэтому вы можете заставить систему переключаться быстрее, чем это было бы необходимо без этого.

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

Вы можете попробовать переключиться на среду рабочего стола или оконный менеджер, который потребляет меньше ресурсов, например, LXDE или IceWM. На работе я использую систему Linux с установленным LXDE и ROX-Filer для минимальной настольной среды. Цель этой системы Linux - запустить VMWare Player, чтобы я мог одновременно запускать Windows XP и Windows 7. Это похоже на то, что вы говорите, и у меня не так много проблем с отзывчивостью при такой большой нагрузке, которую я испытываю. У меня нет никаких проблем отзывчивости с самого Linux (обычно это виртуальные машины , которые иногда заставляют меня ждать второй, и обмен 1 диск между 2 виртуальных машин + 1 OS ожидается , что это) , и всегда были в состоянии приостановить или выключение виртуальных машин всегда , когда Я хочу.

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

DMA включен для ваших дисков? (используйте hdparm) Если вы используете полнодисковое шифрование, это требует, чтобы весь дисковый трафик проходил через ЦП, что сводит на нет большую часть преимуществ DMA. Результатом этого будет то, что высокий трафик диска приводит к скачкам ЦП, что замедляет работу всей системы. (РЕДАКТИРОВАТЬ: чтобы уточнить, отключение DMA ИЛИ использование dm-cryptприведет к высокой загрузке ЦП во время большого дискового трафика)


2
Суть вопроса не в том, что WM вздут, что приводит к замедлению работы системы (вероятно, при нормальной работе), а в том, что ядро ​​неправильно расставляет приоритеты приложениям, когда ему не хватает памяти, и ему приходится входить в систему. тяжелый обмен. У меня была эта проблема на каждом настольном Linux, который я когда-либо использовал, и хотя использование более легких программ или добавление большего количества оперативной памяти может помочь, это не решает корень проблемы.
crazy2be

В моем предыдущем посте я сказал следующее: «Похоже, у вас есть некоторые приложения, которые используют какие-то средства ядра или драйвер, который перегружается». Так что, возможно, узким местом является конкретный модуль ядра. Я не эксперт по ядру, но я уверен, что распределение памяти на стороне ядра, особенно на стороне модуля, работает иначе, чем на стороне пользователя. Загрузка ЦП на стороне ядра также, вероятно, обрабатывается по-разному (не знаю, можете ли вы «приятно» обрабатывать ядро). Я не могу комментировать дальше, не зная конкретных приложений.
LawrenceC

Также, если вы используете FUSE NTFS, это может вызвать медлительность.
LawrenceC

1
Мне известно, что файловая система на основе ОЗУ, такая как tmpfs (очевидно), ускоряет работу ОЗУ и что облегченный WM может немного уменьшить симптомы основной проблемы. Я чувствовал давление при использовании tmpfs из-за плохой отзывчивости, которую может вызвать запись на диск. Тем не менее, спасибо за ваше предложение, особенно часть о DMA, которую я добавил в список возможных тем. Для справки, я считаю, что DMA включен, и я не использую криптографическую файловую систему.
user76871

1

Это распространенная проблема с планировщиком Linux. Система замедляется, чтобы выполнить IO тяжелые действия. Существует не так много вещей, которые вы могли бы сделать, чтобы улучшить ситуацию, если только вы не взломали ядро ​​:)

Может быть, это может помочь:

http://www.phoronix.com/scan.php?page=article&item=linux_2637_video&num=1

http://www.osnews.com/story/24223/Alternative_to_the_200_Lines_Kernel_Patch_that_Does_Wonders_


1
Насколько я помню, эти патчи ядра действительно актуальны только в том случае, если вы компилируете программу или делаете что-то еще, что сильно загружает процессор (или IO?) В терминале , при попытке взаимодействия с приложениями с графическим интерфейсом. Это не помогает в более распространенной ситуации, когда одно приложение с графическим интерфейсом выполняет тяжелую работу, а вы, к сожалению, пытаетесь работать с другим приложением с графическим интерфейсом.
crazy2be

0

Несмотря на то, что этому вопросу уже более двух лет, и ответ @ ypsu отличный, ситуация с системами на базе Linux, ухудшающаяся из-за нехватки ОЗУ, все еще здесь.

Вот мое наблюдение по проблеме: даже если у меня вообще нет свопинга, когда в системе недостаточно памяти, индикатор жесткого диска светится, так как он загружен на 100%. Учитывая этот факт, кажется, что основная причина заключается в том, что ядро ​​пытается освободить память, выгружая что-то, что можно восстановить с диска, и это, скорее всего, общие библиотеки. Поскольку приложения с графическим интерфейсом обычно имеют тонны совместно используемых библиотек, кажется, что системе может показаться, что достаточно просто выгрузить некоторые из них, но это работает только до следующей операции в пространстве пользователя, которая требует эти выгруженные библиотеки обратно. Похоже, что это наиболее вероятный сценарий, вызывающий бесконечный цикл выгрузки общих библиотек и их загрузки обратно.

Существует проект, который действует как демон пользовательского пространства, убивающий наиболее ресурсоемкие процессы, пока не стало слишком поздно: https://github.com/rfjakob/earlyoom

Кроме того, я использовал контейнеры Docker с разумными пределами памяти для приложений, требующих памяти (например, Chrome).

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.