Memory Leak - und danach?



  • Hallo!

    Ich bin mir nicht mehr sicher aber ich meine gelesen(gehört?) zu haben, dass moderne Betriebssysteme (Windows XP, 2003,...) Speicherlöscher mittlerweile "entdecken".
    Also meine App verursacht beim Beenden ein Speicherloch. Normalerweise ist dieser Speicherbereich erst wieder nach dem Rechnerneustart verfügbar. Bei den moderneren wird der aber wieder während der laufenden Sitzung zur Verfügung gestellt. Ist diese Information korrekt?

    P.S.: Wie sieht das unter Linux aus?



  • Grundsätzlich kannst du dich auf sowas nciht verlassen, räum deinen Kram also selber auf! Gehört einfach zur guten Sitte.
    Es mag sein das einige Betriebsysteme sehen das sich ein Programm beendet hat und den Speicher freigeben, aber verlassen sollte amn sich darauf nicht!



  • Tut mir leid, aber falsch 😉

    Wenn Du dem OS den Speicher nicht zurückgibst, wird es nicht entscheiden, dass Du ihn nicht mehr brauchst. Es wird sich höchstens weigern, Dir weiteren Speicher zuzuteilen.

    Sowas kann nur funktionieren wenn die "Benutzer" des allokierten Speichers überwacht werden (etwa durch Referenzzählung), und das nennt man dann Garbage Collection, die Standard C++ bekanntlich nicht mitbringt.

    EDIT:
    Hups, habe ich da was falsch verstanden?
    Ist mit "Neustart" ein Rechnerneustart oder ein Programmneustart gemeint?

    EDIT2:
    Falls zweiteres, ein beendetes Programm abzuräumen bereitet modernen BS keine Probleme (nichtmal Windows :D) - aber ich schliesse mich Storm an, dass Du das Problem nicht umschiffen sondern aufspüren solltest.



  • Storm.Xapek.de schrieb:

    Grundsätzlich kannst du dich auf sowas nciht verlassen, räum deinen Kram also selber auf! Gehört einfach zur guten Sitte.
    Es mag sein das einige Betriebsysteme sehen das sich ein Programm beendet hat und den Speicher freigeben, aber verlassen sollte amn sich darauf nicht!

    Um Himmels Willen. Ich sorge stets dafür meine Speicher aufzuräumen. Das OS als etvl. GC ausnutzen ist nicht sonderlich elegant. 🙂

    Es war nur eine generelle Frage, da Speicherlöcher immer mal auftreten können. Ich arbeite derzeit an Webapplikationen. Deshalb interssiert mich ob das Server-OS sich im Fall des Falles darum kümmert. Nicht das der Speicher nach 1000 Aufrufen in die Knie geht.



  • Gerade bei servern sit es wichtig penibel darauf zu achten das kein speicher "verloren" geht. Die Programme sollen schließelich zum Teil monate laufen, und oft ist ein reboot inakzeptabel. Wenn du darauf achtest hast du kein Problem, fals dennoch etwas schiefgeht kannst du immernoch hoffen das ein wunder geschieht.



  • LordJaxom schrieb:

    EDIT:
    Hups, habe ich da was falsch verstanden?
    Ist mit "Neustart" ein Rechnerneustart oder ein Programmneustart gemeint?

    EDIT2:
    Falls zweiteres, ein beendetes Programm abzuräumen bereitet modernen BS keine Probleme (nichtmal Windows :D) - aber ich schliesse mich Storm an, dass Du das Problem nicht umschiffen sondern aufspüren solltest.

    Habe es mal geändert. Ich meinte Rechnerneustart. Aber das OS räumt also schon nach dem Programmneustart/-ende und auch nach einem Programmabsturz auf, richtig?

    Storm.Xapek.de schrieb:

    Gerade bei servern sit es wichtig penibel darauf zu achten das kein speicher "verloren" geht. Die Programme sollen schließelich zum Teil monate laufen, und oft ist ein reboot inakzeptabel. Wenn du darauf achtest hast du kein Problem, fals dennoch etwas schiefgeht kannst du immernoch hoffen das ein wunder geschieht.

    Das ist auch mein Ziel. Aber ich wollte einfach mal für den Fall der Fälle fragen. 🙂



  • Was du gehört hast gilt für Programmierer mit Java und (was ja moderner trend von WinXP ist) - fürs MS .NET Framework. Der überprüft, ob du speicher "verloren" hast und macht den frei. ABER: das passiert nur, wenn dem system das frei speicher ausgeht, außerdem ist es eine recht lange sache, bringt performance-verlust.

    Also, grundsätzlich: immer den speicher selber aufräumen. Wenn du eine Serveranwendung programmierst, dann wäre trotzdem .NET gute wahl - denn niemand ist perfekt, irgendwas geht dir irgendwann verloren, und .NET sorgt dafür, das es keine instabilität deswegen gibt



  • Maverick89 schrieb:

    Was du gehört hast gilt für Programmierer mit Java und (was ja moderner trend von WinXP ist) - fürs MS .NET Framework. Der überprüft, ob du speicher "verloren" hast und macht den frei. ABER: das passiert nur, wenn dem system das frei speicher ausgeht, außerdem ist es eine recht lange sache, bringt performance-verlust.

    Das heißt, es wird auch nichts nach dem Programmende aufgeräumt obwohl die interne Prozessverwaltung des OS ja sieht, dass der Speicherbereich des gerade geschlossenen Prozesses nicht leer ist.

    Maverick89 schrieb:

    Also, grundsätzlich: immer den speicher selber aufräumen. Wenn du eine Serveranwendung programmierst, dann wäre trotzdem .NET gute wahl - denn niemand ist perfekt, irgendwas geht dir irgendwann verloren, und .NET sorgt dafür, das es keine instabilität deswegen gibt

    An und für sich stimme ich dem zu. Auch gerade bei Webapplikationen ist das .NET Framework eine wahre Goldgrube. Unter anderem laufen .NET Apps leider nicht ohne weiteres auf Linuxsystemen. Und Mono kann ich leider nicht auf dem Linuxserver installieren.



  • Das heißt, es wird auch nichts nach dem Programmende aufgeräumt obwohl die interne Prozessverwaltung des OS ja sieht, dass der Speicherbereich des gerade geschlossenen Prozesses nicht leer ist.

    also ich meinte das run-time.

    nach beenden des prozesses ist was anderes. Ich glaub dass es bei NT+ aufgeräumt wird, genau kann ichs dir nicht sagen, aber man kann es ja leicht ausprobieren.



  • HaJo. schrieb:

    Das heißt, es wird auch nichts nach dem Programmende aufgeräumt obwohl die interne Prozessverwaltung des OS ja sieht, dass der Speicherbereich des gerade geschlossenen Prozesses nicht leer ist.

    Lass Dir nix einreden. Maverick89 redet von Garbage Collection, nicht von Memory Management 😉

    Wenn die blöde SharpDevelop-Beta mal wieder den Rechner runterzieht, weil er meint 850 MB virtuellen Speicher belegen zu müssen, kille ich den Prozess und der Speicher ist wieder frei. (Falls jetzt das Argument kommt SharpDevelop ist .NET - a) wird es beim Installieren native compiliert und b) überlässt ein Prozess-Kill dem Framework wenig Gelegenheit aufzuräumen)

    EDIT: Ok, hat sich gerade (s.o.) geklärt

    Maverick89 schrieb:

    Also, grundsätzlich: immer den speicher selber aufräumen. Wenn du eine Serveranwendung programmierst, dann wäre trotzdem .NET gute wahl - denn niemand ist perfekt, irgendwas geht dir irgendwann verloren, und .NET sorgt dafür, das es keine instabilität deswegen gibt

    An und für sich stimme ich dem zu.

    Ich auch (nur dass das nicht den Anschein erweckt 😉 )



  • Alle moderneren BS "ünterstuetzen" das, mehr oder weniger gut ...

    Wenn du in unix nen prozess killst, wird auch aller Speicher den er beim Speichermanager allokiert hat (Pid), wieder freigegeben

    Windows genau so ... zumindest behaupted das MS ^^
    Kann man aber leicht selber pruefen mit den entsprechenden Tools, ... Speicher allokieren, programm beenden lassen / oder per Taskmanager killen, und voiala, weg isser ^^

    Probleme sind eher, wennd er prozess sich ned 100% killen laaesst, und verwaist irgendwo noch als leiche dahinduempelt.

    Das entbindet natuerlich nicht davon seinen speicher selber wieder freizugeben ... gruende dafuer gibt es tausende ...

    Ciao ..



  • RHBaum schrieb:

    Probleme sind eher, wennd er prozess sich ned 100% killen laaesst, und verwaist irgendwo noch als leiche dahinduempelt.

    Und ein weiteres Problem dürfte sein, daß ein Programm mitunter mehr reserviert als nackten Speicher - und File-Handles oder Datenbank-Verbindungen wird dein Betriebssystem ziemlich sicher NICHT freigeben, wenn du das Programm killst (oder ohne die nötigen Aufräumarbeiten beendest).



  • Filehandles räumt das Betriebssystem schon auf (zumindest Linux und alle unixoide, die ich so kenne), bei Datenbankressourcen hängt ja meist noch ein Server dahinter, der seinerseits Resourcen für den Client belegt hält (zumindest bis zu irgendeinem Timeout) wenn dieser gekillt wird.



  • Unter Unix werden z.B. SysV-Shared-Memory-Segmente nicht automatisch freigegeben, temporäre Dateien werden natürlich auch nicht automatisch gelöscht. Der Rest, insbesondere normal allozierter Speicher, natürlich schon! Ein Speicherleck, was über das Programmende hinweg besteht, ist schon ein ziemlich harter Brocken und sollte unbedingt gefixt werden.



  • LordJaxom schrieb:

    Filehandles räumt das Betriebssystem schon auf (zumindest Linux und alle unixoide, die ich so kenne)

    Es gibt hier auch Leute, die es tatsächlich gewagt haben, ein MS-System zu verwenden 😉

    Und außerdem waren die Beispiele oben frei aus der Luft gegriffen - wenn das System die verwendeten Ressourcen tatsächlich selber freigeben kann, hast du Glück. Aber es ist besser, du kümmerst dich selber darum, dann bist du auf der sicheren Seite.



  • Wenn du ein Programm (egal ob selbst geschriebenes oder nicht) beendest, dann sind dessen (Speicher-)Resourcen auf JEDEM Betriebssystem (das im Protected Mode läuft, also alle Windows ab 95/NT, alle Unixe [weis nicht genau, aber es gibt bestimmt auch welche die im Real Mode laufen...], etc...) wieder freigegeben.

    Wie das mit anderen Dingen ist, wenn du das Programm einfach killst, ist unterschiedlich:

    1. Socketverbindungen werden normal 'geclosed'. (Bei TCP noch ein client terminated Packet gesendet)
    2. Aus Punkt 1 folgert dann auch, dass alle Datenbank Verbindungen beendet wurden.
    3. Bei OpenGL/DirectX ist mir kein Fehlverhalten bekannt, der Grafikkartenspeicher wird ebenfalls freigegeben, sowie die Fragment/Vertex Shader.
    4. Sehr fehleranfällig sind nach meiner Erfahrung alle Dinge die mit TV Karten zu tun haben, wenn man da nicht richtig deinited dann war es das meistens.
    5. Ansonsten ist das Verhalten auch stark von der Platform abhängig.

    Grundsätzlich ist nur noch zu sagen, wie auch schon ein Vorgänger sagte: Niemals mit dem Ziel programmieren, dass das OS "das schon macht". Immer schön Destruktoren benutzen, zu jedem new/malloc gehört auch ein delete/free.



  • Was sagt ihr dazu: http://www.fachschaft.informatik.tu-darmstadt.de/forum/viewtopic.php?t=4057?
    Aehnlichen Effekt hatte ich unter Linux. Als ich mit der Arbeit fertig war und Quake spielen wollte, ruckelte es mit 5fps vor sich hin.


Anmelden zum Antworten