2009-04-02 2 views
13

У меня есть VPS с не очень большой памятью (256 Мб), которую я пытаюсь использовать для разработки Common Lisp с SBCL + Hunchentoot для написания простых веб-приложений , Похоже, что большой объем памяти используется, не делая ничего особо сложного, и через некоторое время на страницах обслуживания у него заканчивается память, и либо он сходит с ума, используя все свопы, либо (если нет свопа) просто умирает.Устранение и использование памяти в Common Lisp (SBCL)

Поэтому мне нужна помощь:

  • Узнайте, что использует всю память (если это библиотека или меня, особенно)
  • Ограничить объем памяти, который SBCL разрешается использовать, чтобы избежать массовые количества подкачки
  • Обращайтесь с вещами чисто, когда память закончится, а не сбой (поскольку это веб-приложение, я хочу, чтобы оно продолжалось и пыталось очистить).

Я предполагаю, что первые два являются достаточно простыми, но третье возможно даже? Как люди справляются с нехваткой памяти или ограниченными условиями памяти в Lisp?

(Кроме того, я отмечаю, что 64-разрядный SBCL, по-видимому, использует буквально вдвое больший объем памяти, чем 32-разрядный. Ожидается ли это? Я могу запустить 32-разрядную версию, если она сэкономит много памяти)

ответ

13

Чтобы ограничить использование памяти SBCL, используйте опцию --dynamic-space-size (например, sbcl --dynamic-space-size 128 ограничит использование памяти до 128M).

Чтобы узнать, кто использует память, вы можете позвонить по телефону (room) (функция, указывающая, сколько памяти используется) в разное время: при запуске, после загрузки всех библиотек, а затем во время работы (из курса, звоните (sb-ext:gc :full t) до помещения, чтобы не измерить мусор, который еще не был собран).

Кроме того, для измерения распределения памяти можно использовать SBCL Profiler.

+0

Не могли бы вы добавить ссылку на что-то о профилировщике SBCL, пожалуйста? :) –

+2

Существует описание профилировщика в руководстве SBCL по адресу http://www.sbcl.org/manual/Deterministic-Profiler.html –

+0

Удивительно, спасибо! –

1

Я бы не удивился 64-разрядному SBCL, использующему в два раза больше, поскольку он, вероятно, будет использовать 64-битную ячейку, а не 32-разрядную, но не мог точно сказать, не проверив ее.

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

3

Если у вас нет объявлений типа, я бы ожидал, что 64-разрядный Lisp займет в два раза больше пространства 32-битного. Даже простой (маленький) int будет использовать 64-битный кусок памяти. Я не думаю, что он будет использовать меньше машинного слова, если вы не заявите об этом.

Я не могу помочь с # 2 и # 3, но если вы выясните № 1, я подозреваю, что это не будет проблемой. Я видел экземпляры SBCL/Hunchentoot на протяжении веков. Если я использую возмутительный объем памяти, это, как правило, моя собственная ошибка. :-)

4

Узнайте, что использует всю память (если это библиотеки или меня, особенно)

Аттила Lendvai имеет некоторые SBCL специфичный код, чтобы узнать, где выделенному объекты поступает из ,Обратитесь к http://article.gmane.org/gmane.lisp.steel-bank.devel/12903 и напишите ему личное письмо, если необходимо.

Обязательно попробуйте другую реализацию, желательно с точным GC (например, Cllozure CL), чтобы убедиться, что это не утечка, специфичная для реализации.

Ограничить объем памяти, который SBCL разрешается использовать, чтобы избежать массовых количеств замены

уже ответили другие.

ручки вещи чисто, когда память работает аут, а не врезаться (так как это веб-приложение, которое я хочу, чтобы продолжать и попытаться очистить).

256MB плотно, но в любом случае: планируйте повторяющуюся (возможно, 1 с) временную нить, которая проверяет оставшееся свободное пространство. Если свободное пространство меньше X, используйте exec(), чтобы заменить текущий образ процесса SBCL на новый.

Смежные вопросы