2009-11-17 13 views
5

Ich habe ein Handle-Leck in einem großen alten Programm. Mit sysinternals handle.exe leitete ich ab, dass der Typ von Handle, der undicht ist, ein "Event" -Handle ist. Aber ich bin nicht sicher, welche Teile meines Codes ich betrachten sollte. Gibt es irgendwo eine Liste von Funktionen, die Handles zu Ereignissen zurückgeben?Was ist ein Ereignishandle?

EDIT: Es gibt keine einzige Instanz von CreateEvent, CreateEventEx oder OpenEvent im gesamten Programm.

Antwort

2

Wie viel von diesen ausgetretenen Griffen sehen Sie?

Ereignisse werden implizit durch kritische Abschnitte erzeugt (siehe InitializeCriticalSection ua) und wahrscheinlich einige andere Win32-Elemente, an die ich mich im Moment nicht erinnern kann. Sie können auch von dem Framework erstellt werden, das Sie (falls vorhanden) verwenden, z. B. MFC, oder von Bibliotheken, die Sie verwenden.

Um das Leck aufzuspüren, können Sie einen Nur-Druck-Haltepunkt verwenden. Treten Sie in die CreateEvent-Funktion ein (mit der Assembly-Ansicht) und setzen Sie einen Haltepunkt auf die erste Anweisung. Klicken Sie dann mit der rechten Maustaste auf den Haltepunkt, wählen Sie "When Hit ..." und bearbeiten Sie die Optionen, damit sie nicht in den Debugger einbricht, sondern einige nützliche Informationen ausgibt (siehe z. B. $ CALLER-Makro). Dann starte deine App ... und sei darauf vorbereitet, ein RIESIGES Protokoll zu sehen. Wenn ein echtes Leck vorliegt, wird im Protokoll ein sich wiederholendes Muster angezeigt, das den Täter identifiziert.

+0

Nach dem anfänglichen Aufruhr hat sich das Programm darauf eingestellt, ungefähr ein oder zwei pro Sekunde zu erzeugen. - Diese Antwort klingt sehr machbar, aber ich kann es erst morgen ausprobieren. Prost. – Mick

0

Soweit ich weiß, sind fast die einzigen Dinge, die ein Ereignis erstellen CreateEvent und CreateEventEx. Ziemlich viele andere Funktionen können ein Handle auf ein Ereignis (zB WaitForMultipleObjects) zurückgeben, aber es ist ein Handle, das Sie zuvor erstellt und übergeben ..

Bearbeiten: Da Ihr Code anscheinend nicht die Veranstaltung direkt erstellt, könnten Sie Ich möchte mit Umleitungen beginnen, Aufrufe von CreateEvent (Ex) zu betrachten, und den Stack zurückverfolgen, um zu sehen, welcher Teil des Codes sie verursacht, und was er erstellt, um sie zu erstellen.

1

Wie andere Leute erwähnt haben, werden CreateEvent/CreateEventEx zum Erstellen von "Event" -Zeichen verwendet. Diese stellen Synchronisationsobjekte dar, die häufig zum Gate-Zugriff verwendet werden, Signale (potentiell) an andere Threads liefern und auch als Basis für Sperren verwendet werden können.

Wenn Sie versuchen, ein Leck mit Event-Handles zu debuggen, sollten Sie versuchen, nach Stellen zu suchen, an denen CreateEvent (Ex) ohne ein entsprechendes CloseHandle() aufgerufen wird. Je nachdem, welche Frameworks Sie zum Abrufen von Ereignissen verwendet haben, werden Sie möglicherweise bei der Bereinigung auch fehlen, wenn sie Mitglieder eines anderen Objekts/einer anderen Struktur sind (z. B. eine generische LEVEL-Membervariable, die beim Bereinigen übersprungen wird, oder ein Zeiger auf einen GRIFF usw.).

Wenn Sie sich nicht erinnern, diese Objekte in Ihrem eigenen Code erstellt zu haben, ist es möglich, dass Sie eine analoge Close() - oder andere Bereinigungsmethode für eine andere Klasse oder einen anderen Anbieter, der sie intern verwendet, nicht verwenden. Dinge, die Hintergrundverarbeitung, Signalisierung oder Methoden bereitstellen, um auf den Abschluss von Operationen zu warten, sind hier die üblichen Verdächtigen.

Event erstellen Griffe
CreateEvent Function @ MSDN
CreateEventEx Function @ MSDN

Cleanup
CloseHandle Function @ MSDN

1

Griffe Wenn Sie nicht wissen, was DLLs oder Komponenten von Drittanbietern fordern Create oder CreateEventEx dann die Dependency Walker verwenden, um zu sehen Was jede DLL importiert:

http://www.dependencywalker.com/ (es ist kostenlos)

Das wird zumindest dazu beitragen, das Problem auf eine bestimmte Reihe von Interaktionen einzugrenzen - dann müssen Sie alle Aufrufe dieser Bibliothek betrachten und überprüfen, ob alles korrekt bereinigt ist.

1

Auch wenn Sie Events nicht direkt selbst erstellen, kann und wird das Betriebssystem oder ein anderer Bibliothekscode dies auch tun. Vielleicht möchten Sie sich die Möglichkeit ansehen, dass eine andere Ressource, die Ihre Anwendung gerade öffnet/erstellt, nicht bereinigt wird.Es ist möglich, dass du etwas anderes leckst, aber dieses Ding bringt ein Event-Objekt für die Fahrt mit.

Es könnte helfen, einen Debugger Breakpoint auf CreateEvent (und Freunde) zu setzen, um zu sehen, was es erstellt, aber ich wäre nicht überrascht, wenn das oft genug auftritt, dass Ihr Problem im Rauschen verloren geht.