Есть ли допустимый предел утечек памяти?

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

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

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


person Jim    schedule 24.10.2008    source источник


Ответы (11)


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

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

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

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

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

HTH.

ваше здоровье,

Роб

person Rob Wells    schedule 24.10.2008

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

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

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

person Steve Jessop    schedule 24.10.2008

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

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

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

РЕДАКТИРОВАТЬ

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

person Tim    schedule 24.10.2008
comment
но, как я упоминаю ниже, вы должны быть уверены, что это настоящие утечки, а не просто ложные срабатывания от наивно реализованной системы. - person Rob Wells; 07.11.2008
comment
Кроме того, если у вас есть программа, которая будет работать в течение трех лет подряд, вы не можете позволить себе утечку чего-либо, и уж тем более ничего, кроме разовой утечки. - person Jonathan Leffler; 22.01.2009

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

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

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

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

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

person Tamas Czinege    schedule 24.10.2008

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

person Toon Krijthe    schedule 24.10.2008
comment
В основном это так, но утечки на сервере можно немного уменьшить за счет перезапуска приложений (периодических перезапусков серверных процессов). Тем не менее, лучше очистить его. - person Kristopher Johnson; 24.10.2008
comment
Я думаю, что такие периодические перезапуски - это всего лишь вариант подхода к отладке, в котором говорится, что данные в этой точке кода неверны, поэтому измените их, а не выясняйте, что в первую очередь делает их неправильными. Я бы никогда не стал использовать сервер, который нужно периодически перезапускать. - person rmeador; 24.10.2008
comment
На серверах может происходить утечка памяти при запуске. Пока это фиксированные накладные расходы на запуск, это не приведет к остановке сервера. Например. globals без надлежащего dtor не сильно повредят. - person MSalters; 24.10.2008
comment
Ваше утверждение неверно. С практической точки зрения утечки памяти могут быть допустимы на серверах, если: (a.) Они недостаточно значительны, чтобы повлиять на пользователей (b.) Можно использовать такую ​​стратегию, как регулярные перезапуски, не влияя на доступность. - person johnstok; 27.10.2008

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

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

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

person T.E.D.    schedule 24.10.2008
comment
Это известно как «устойчивое состояние». Если программа достигает устойчивого состояния, утечки нет. - person QBziZ; 24.10.2008

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

person GavinCattell    schedule 24.10.2008

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

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

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

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

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

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

person Blaisorblade    schedule 12.01.2009
comment
Я обычно использую deleaker - (valgrind для linux) - person John Smith; 28.12.2011

Согласно комментариям Роба Уэллса о Purify, загрузите и опробуйте некоторые другие инструменты. Я использую BoundsChecker и AQTime, и за эти годы я видел разные ложные срабатывания. Обратите внимание, что утечка памяти также может быть в стороннем компоненте, который вы можете исключить из анализа. Например, у MFC в первых версиях просмотра было несколько утечек памяти.

ИМО, утечки памяти следует отслеживать для любого кода, который входит в базу кода, которая может иметь долгую жизнь. Если вы не можете отследить их, по крайней мере, отметьте, что они существуют для следующего пользователя того же кода.

person SmacL    schedule 24.10.2008

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

person TheMarko    schedule 24.10.2008

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

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

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

person Kieron    schedule 22.01.2009