C++ Speicherverbrauch beobachten/Memory Leak Detection

badday

Commander
Registriert
Sep. 2007
Beiträge
3.023
Moin zusammen,

ich arbeite momentan an einem Programm, dass im 24/7 Einsatz sein wird. Dabei ist zu beobachten, dass es offenbar ein memory Problem gibt, da es nach und nach immer mehr Speicher belegt.

Also habe ich kurzerhand valgrind's memcheck angeworfen und siehe da: Keine verdächtigen Sachen erkennbar nach rund 12h.
Auch valgrind's massif half mir nicht weiter.

Ich suche daher nach einem Tool, dass es mir erlaubt, möglichst übersichtlich die dynamischen Speicherallokierungen zu verfolgen, am besten in Echtzeit. Möglicherweise ist die Ursache auch in einer externen lib, gibt es vll. sogar die Möglichkeit, durch trace backs etc. zu verfolgen, von wo welcher Anteil des gesamten Speicherverbrauchs allokiert wurde?


Ich wäre sowohl für konkrete Tools als auch allgemeine Tipps sehr dankbar.



Gruß,

badday
 
Hi,

schau Dir mal die Google-Perftools an, und dort speziell den tcmalloc Heap-Profiler.

Wenn inuse-Space bzw inuse-Objects nichts aufzeigen, guck mal nach alloc-Space bzw alloc-Objects.

Möglicherweise hast du auch ein Fragmentierungsproblem, dann wird es etwas haariger.

Gruß

Btw: Wenn memcheck keine Leaks beim Beenden anzeigt, heißt das i.a.R., dass Objekte irgendwo gemanaged gehalten werden, die beim Beenden auch sauber weggeräumt werden - aber eben nicht an dem Zeitpunkt, an dem es sein müsste. Leg den Fokus mal auf Objekte, die zu Hauf erzeugt werden - Fliegengewichte z.B.
 
Zuletzt bearbeitet:
Hmm, was heißt denn "offenbar"? Wie hast du das Leak verifiziert? Woher kommt die Sicherheit?
Ansonsten:
Wie wär's mit DUMA? Oder du implementierst kurzerhand deine eigene Version von malloc/new.
 
Zuletzt bearbeitet:
Wenn dein Programm auf einem UNIX läuft, könntest du mal Valgrind probieren. Das liefert dir sehr übersichtlich welche Teile des Programms leaken.
 
@ghorst:
Ersten Beitrag gelesen? :) valgrind hat er schon benutzt. ;)

@badday:
Wie genau äußert sich der erhöhte Speicherverbrauch? Nur in VSS oder auch RSS? Hast du mal eine Langzeitaufzeichnung mit z.B. atop gemacht?

Stirbt der Prozess eigentlich irgendwann, wegen OutOfMemory? Evtl. auch mal Overcommit ausschalten, dann findet man solche Sachen schneller :) Google mal nach /proc/sys/vm/overcommit*. Hängt u.U. von deinem Kernel ab.

Btw, tcmalloc solltest du mit LD_PRELOAD laden, dann erwischt du definitiv auch jede andere dynamisch geladene Bibliothek.
 
Zuletzt bearbeitet:
So, mal der Reihe nach :)

schau Dir mal die Google-Perftools an, und dort speziell den tcmalloc Heap-Profiler.
Habe ich getan und das ganze via

Code:
env HEAPPROFILE=/home/username/mybin.hprof LD_PRELOAD="/usr/lib64/libtcmalloc.so"  exec
ausgeführt, womit er auch eine Datei erstellt. Allerdings werde ich nicht ganz schlau daraus, wie ich diese nun öffne,
Code:
pprof -gv mybin.hprof.0001
scheint ja nicht zu funktionieren, offenbar habe ich da was falsch verstanden :(
Hast du mal eine Langzeitaufzeichnung mit z.B. atop gemacht?
Nein, hatte ich noch nicht. Habe mir das Programm eben kurz angeschaut. Kann man da einen nach PID gefilterten Log erstellen?

Stirbt der Prozess eigentlich irgendwann, wegen OutOfMemory?
Müsste ich testen, würde aber Tage dauern. Ich kann es dir nicht sagen, da der Server, auf dem es lief, dann nicht mehr erreichbar war ;)

Evtl. auch mal Overcommit ausschalten, dann findet man solche Sachen schneller
Soweit ich das überblicke kann man damit einstellen, ob mehr memory allokiert werden kann, als eigentlich vorhanden?

Hmm, was heißt denn "offenbar"? Wie hast du das Leak verifiziert? Woher kommt die Sicherheit?
Offenbar heißt eben nicht sicher, aber es deutet vieles darauf hin. Wenn ich das Leak verifiziert hätte, wäre ich schon einen guten Schritt weiter ;)

Wie wär's mit DUMA?
Denke das sollte mit tcmalloc auch möglich sein (?).



Danke schonmal für die vielen hilfreichen Antworten :)



Gruß,

badday
 
badday schrieb:
Habe ich getan und das ganze via

Code:
env HEAPPROFILE=/home/username/mybin.hprof LD_PRELOAD="/usr/lib64/libtcmalloc.so"  exec
ausgeführt, womit er auch eine Datei erstellt. Allerdings werde ich nicht ganz schlau daraus, wie ich diese nun öffne,
Code:
pprof -gv mybin.hprof.0001
scheint ja nicht zu funktionieren, offenbar habe ich da was falsch verstanden :(
Die 0001er ist das Initial Profile. Du kannst tcmalloc sagen, wann es Profiles schreiben soll. Default ist IIRC alle 100MB. Je nach Anwendungsfall kann man hier ein wenig tunen. Einfach mal die Doku lesen. :)

Mit pprof kannst du dir die Profile eigentlich alle anzeigen lassen. GhostView ist installiert? Dann kriegst du einen hübschen grafischen Tree.

badday schrieb:
Nein, hatte ich noch nicht. Habe mir das Programm eben kurz angeschaut. Kann man da einen nach PID gefilterten Log erstellen?
Du kannst mit der nicht-interaktiven Version ein Protokoll aufzeichnen lassen, dass du hinterher ausgeben und parsen kannst. Ist u.U. ein wenig mühsam, hat aber für meine Zwecke immer gut funktioniert.

badday schrieb:
Soweit ich das überblicke kann man damit einstellen, ob mehr memory allokiert werden kann, als eigentlich vorhanden?
Genau. Mit overcommit kannst du z.B. bei nem 8GB-System ein malloc von 50GB machen. Solange du die Pages nicht anfasst, werden diese nicht tatsächlich allokiert und damit resident. Vergleich's mit dem Überbuchen von Flugzeugen. Da werden auch mehr Sitzplätze verkauft als das Flugzeug hat, weil mit Absagen gerechnet wird.

Schau doch mal bitte wegen VSS und RSS, das wäre hilfreich. :) (kennst du den Unterschied zwischen virtual set size und resident set size?)
 
Mit pprof kannst du dir die Profile eigentlich alle anzeigen lassen. GhostView ist installiert?
Jetzt ist es installiert. Nur: Wie öffne ich eine .heap Datei damit?
Laut Doku müsste das so gehen:
pprof --gv gfs_master /tmp/profile.0100.heap
http://google-perftools.googlecode.com/svn/trunk/doc/heapprofile.html
Also generisch ausgedrückt:
pprof --gv /path/to/exec /path/to/log.max.heap
? Habe das Gefühl, ich sitze da etwas auf dem Schlauch.

kennst du den Unterschied zwischen virtual set size und resident set size?
VSS bezieht sich wohl auf verschiedene storages, bietet aber ein einheitliches, Ram-like, Interface, rss nur auf den Ram (?).


Gruß,

badday
 
Zurück
Oben