Обнаружение утечки дескриптора файла с Win32 C ++ - PullRequest
8 голосов
/ 24 ноября 2008

Есть ли какой-нибудь способ обнаружить утечки дескриптора файла при завершении программы?

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

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

Ответы [ 10 ]

7 голосов
/ 25 ноября 2008

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

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

5 голосов
/ 28 июня 2010

Я использовал команду! Htrace windbg.

!htrace -enable
!htrace -snapshot
!htrace -diff

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

Это хорошо сработало для меня.

4 голосов
/ 14 января 2009

Если вы не можете позволить себе BoundsChecker или подобное ...

Один прием, который я использовал, - заменить CreateFile и т. Д. Моими собственными обертками. В дополнение к возвращению значения дескриптора, они делают запись __FILE__ и __LINE__ для каждого дескриптора. Вам также нужно будет обернуть CloseHandle, чтобы убедиться, что правильно закрытые маркеры не вызывают ложных срабатываний.

Это так же просто, как:

// StdAfx.h
#include <windows.h>
#undef CreateFile
#if defined(UNICODE)
 #define CreateFile DbgCreateFileW
#else
 #define CreateFile DbgCreateFileA
#endif

// etc.

Затем вы определяете DbgCreateFileW и DbgCreateFileA где-то в своем коде.

Это предполагает, что у вас есть контроль над соответствующими частями кода. Если нет, то вы можете сделать что-то подобное, используя (например) Microsoft Detours (вам потребуется лицензия, чтобы включить его в выпущенный продукт, но я считаю, что его можно использовать бесплатно для отладки / тестирования / и т. Д.)

Однако в долгосрочной перспективе вам следует обратить внимание на преобразование кода в «умный» тип дескриптора, который автоматически вызывает CloseHandle, когда он выходит из области видимости.

4 голосов
/ 25 ноября 2008

Вы также можете использовать MS Application Verifier .

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

Я предлагаю этот инструмент Memory Validator

это очень приятно.

1 голос
/ 27 ноября 2008

Еще один совет - SysInternals FileMon ( Link ).

Показывает активность файловой системы, поэтому он должен помочь вам в поиске открытых дескрипторов.

1 голос
/ 25 ноября 2008

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

1 голос
/ 24 ноября 2008

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

0 голосов
/ 25 февраля 2009

windbg или ntsd имеют расширение! Handle, которое сообщает вам, какие дескрипторы открыты в приложении. Я полагаю, вы могли бы поставить точку останова в конце вашей программы и вывести туда дескрипторы.

Может также быть что-то, что вы можете сделать в powerdbg (http://www.codeplex.com/powerdbg) для автоматизации этого процесса.

Конечно, это предполагает, что ваше время обходится дешевле, чем покупка решения:)

0 голосов
/ 14 января 2009

Как заявлял MadKeithV, вы можете использовать RAII для отличного эффекта.

Также простым способом (и бесплатным) является использование Visual Leak Detector . Это не идеальный, но хороший способ убедиться, что у вас есть free'd / delete [] d / close'd и т. Д.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...