Есть ли приемлемый предел для утечек памяти? - PullRequest
20 голосов
/ 24 октября 2008

Я только начал экспериментировать с SDL в C ++, и я подумал, что регулярная проверка на утечки памяти может быть хорошей привычкой формироваться на ранних этапах.

Имея это в виду, я запускал свои программы 'Hello world' через Valgrind для выявления любых утечек, и хотя я удалил все, кроме самых простых SDL_Init() и SDL_Quit() операторов, Valgrind все еще сообщает 120 потеряно байтов и 77 кбайт по-прежнему достижимы.

Мой вопрос: существует ли приемлемый предел для утечек памяти, или я должен стремиться сделать весь мой код полностью без утечек?

Ответы [ 11 ]

17 голосов
/ 24 октября 2008

Будьте осторожны, чтобы Valgrind не улавливал ложные срабатывания при измерениях.

Многие наивные реализации анализаторов памяти отмечают потерю памяти как утечку, когда это не совсем так.

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

Кстати, я никак не связан с IBM. Я только что широко использовал Purify и буду ручаться за его эффективность.

Редактировать: Вот отличная вводная статья , посвященная мониторингу памяти. Это специфично для Purify, но обсуждение типов ошибок памяти очень интересно.

НТН.

ура

Rob

11 голосов
/ 24 октября 2008

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

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

Избегайте неаккуратного программирования - уже есть достаточно плохих программистов - миру не нужен еще один.

EDIT

Я согласен - многие инструменты могут давать ложные срабатывания.

11 голосов
/ 24 октября 2008

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

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

Мне редко удавалось достичь нуля по этой метрике, что эквивалентно наблюдению за использованием ползучей памяти в отличие от потерянных блоков. У меня была одна библиотека, в которой она оказалась настолько неудобной, с кешами и мебелью пользовательского интерфейса, и так далее, что я просто трижды запускал свой тестовый набор и игнорировал любые «утечки», которые не возникали в виде кратных трех блоков. Я все еще улавливал все или почти все настоящие утечки и анализировал хитрые сообщения, как только убрал с потолка висящие фрукты. Конечно, слабые стороны использования набора тестов для этой цели заключаются в том, что (1) вы можете использовать только те его части, которые не требуют нового процесса, и (2) большинство обнаруженных вами утечек являются ошибкой кода теста , а не код библиотеки ...

8 голосов
/ 24 октября 2008

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

Вам нужно протестировать ваше приложение примерно за час, а затем вычислить утечку памяти. Таким образом, вы получите утечку памяти в байтах / минутах.

Теперь вам нужно оценить среднюю продолжительность сеанса вашей программы. Например, для notepad.exe 15 минут звучат как хорошая оценка для меня.

Если ( средняя продолжительность сеанса) * (утечка байтов / минута)> 0,3 * (пространство памяти, обычно занимаемое вашим процессом) , то вам, вероятно, следует приложить еще больше усилий для уменьшения утечек памяти. Я только что составил 0,3, используйте здравый смысл, чтобы определить ваш приемлемый порог.

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

7 голосов
/ 24 октября 2008

Для настольного приложения небольшие утечки памяти не являются реальной проблемой. Для сервисов (серверов) утечки памяти не допускаются.

6 голосов
/ 24 октября 2008

Большинство ОС (включая Windows) вернут всю выделенную память программы, когда программа выгружена. Это включает в себя любую память, которую программа могла потерять.

Исходя из этого, моя обычная теория заключается в том, что утечка памяти при запуске совершенно нормально, но не ОК, чтобы делать это во время выполнения.

Таким образом, на самом деле вопрос не в том, протекает ли у вас какая-либо память, а в том, если вы постоянно вытекаете ее во время выполнения вашей программы. Если вы используете свою программу какое-то время, и независимо от того, что вы делаете, она остается потерянной, а не увеличивающейся на 120 байт, я бы сказал, что вы отлично справились. Двигайся.

2 голосов
/ 12 января 2009

Похоже, разработчики SDL не используют Valgrind, но я в основном забочусь только об этих 120 потерянных байтах.

Имея это в виду, я запускал свои программы 'Hello world' через Valgrind для обнаружения любых утечек, и хотя я удалил все, кроме самых простых операторов SDL_Init () и SDL_Quit (), Valgrind все еще сообщает 120 потеряно байтов и 77 кбайт по-прежнему достижимы.

Что ж, в Valgrind «все еще достижимая память» часто не является утечкой памяти, особенно в такой простой программе. Могу поспорить, что в SDL_Quit () распределение практически отсутствует, поэтому «утечки» - это просто структуры, выделенные SDL_Init () один раз.

Попробуйте добавить полезную работу и посмотрите, увеличатся ли эти суммы; попробуйте сделать цикл полезной работы (например, создать и уничтожить некоторую структуру SDL) и посмотреть, растет ли количество утечек с количеством итераций. В последнем случае вы должны проверить в стеке следы утечек и исправить их.

В противном случае эти 77k утечек считаются «памятью, которая должна быть освобождена в конце программы, но для которой они полагаются на ОС для ее освобождения».

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

2 голосов
/ 24 октября 2008

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

1 голос
/ 22 января 2009

В частности, в случае SDL для Linux в базовой библиотеке X windows есть утечка. Вы ничего не можете с этим поделать (если только вы не хотите попытаться исправить саму библиотеку, что, вероятно, не для слабонервных).

Вы можете использовать механизм подавления valgrind (см. --Suppressions и --gen-suppressions на справочной странице valgrind), чтобы запретить вам беспокоиться об этих ошибках.

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

1 голос
/ 24 октября 2008

Постоянные утечки памяти - это только серьезная проблема, когда они растут со временем, в противном случае приложение выглядит немного больше снаружи (очевидно, здесь тоже есть предел, отсюда и «серьезный»). Когда у вас течет со временем, вы можете быть в беде. Сколько неприятностей зависит от обстоятельств. Если вы знаете , куда идет память, и можете быть уверены, что у вас всегда будет достаточно памяти для запуска программы и всего остального на этой машине, у вас все равно все в порядке. Однако, если вы не знаете, куда идет память, я не стал бы отправлять программу и продолжать копать.

...