Empfehlungsungswerte Tools bzgl Speichermanagement
-
Hi,
bin mittlerweile an meinem zweiten größeren C++ Objekt (und dem ersten mit minimal-sinnvoller Objektorientierung) und bin schon richtig happy, dass es zumindest funktioniert und ich so grob verstanden hab wie sich das bei C++ alles mal einer gedacht hat...
Naja allerdings bin ich eine Woche gehangen nur wegen einem völlig dämlichen Fehler (Überlauf in einem festen Array - der war auch nur zu Debug-Zwecken drin, und deswegen hab ich den nie beachtet) - allerdings in ein paar Structs verschachtelt, so dass der MSVC++ Compiler das Problem nicht erkannt hat, und ich nur so hilfreiche Fehlermeldungen wie "Bad Heap Handle" oder "Zugrifssfehler in nt.dll" bekommen hab - war echt fast am Verzweifeln.
Und jetzt hab ich wieder mal jede Menge Speicherlecks, die ich noch nicht gefunden hab - das gibts doch einige Programme, die auf Speichermanagement überprüfen - vielleicht besser der MS Compiler?
Benützt ihr da irgendetwas in der Richtung, könnt ihr etwas empfehlen?
Schon mal *indeckunggeh* vor den Antworten wie "lern programmieren, dann passiert sowas nicht" - ich komm aus der VB-Ecke, bin da etwas verwöhnt was Compilerhinweise angeht.
Grüße,
rabbit
-
sorry für die Überschrift, bin schon ein bissl müde (vom vielen Proggen ;-)) - empfehlenswerte solls heißen (da jetzt tut man sich schon die ganze Progging-Syntax an, und dann kommt auch diese inkohärente Deutsch-Grammatik dazu ;-))
-
Speicherlecks unter C++ zu bauen ist schon ziemlich schwer...kann es sein das du in C programmierst?
-
roflmao schrieb:
Speicherlecks unter C++ zu bauen ist schon ziemlich schwer...
Nein, ist genauso einfach wie unter C. Allerdings gibt es mehr Alternativen, damit es erst gar nicht soweit kommt.
RabbitsDad schrieb:
Überlauf in einem festen Array - der war auch nur zu Debug-Zwecken drin
Du baust für Debug Zwecke einen Überlauf in dein Programm ein? Nettes Hobby was du da hast.
Eigentlich baut man für Debug Zwecke Abfragen ein, ob ein Überlauf stattgefunden hat.RabbitsDad schrieb:
allerdings in ein paar Structs verschachtelt, so dass der MSVC++ Compiler das Problem nicht erkannt hat
Aktuelle MSC haben zB eine Option für "Buffer Security Checks". Mit der "Verschachtelung in structs" hat das übrigens nichts zu tun.
RabbitsDad schrieb:
Und jetzt hab ich wieder mal jede Menge Speicherlecks, die ich noch nicht gefunden hab
Benutze Container (bzw. Smart Pointer), dann reduziert sich sowas auf ein Minimum.
RabbitsDad schrieb:
Benützt ihr da irgendetwas in der Richtung, könnt ihr etwas empfehlen?
Empfehlen kann ich dir da nichts, da mir die praktische Erfahrung mit solchen Tools fehlt.
Allerdings tauchen hier immer wieder diverse Namen auf, zB valgrind.RabbitsDad schrieb:
ich komm aus der VB-Ecke
Aha, das erklärt einiges.
Ach, und noch was
lern programmieren, dann passiert sowas nicht.
-
RabbitsDad schrieb:
Und jetzt hab ich wieder mal jede Menge Speicherlecks, die ich noch nicht gefunden hab - das gibts doch einige Programme, die auf Speichermanagement überprüfen - vielleicht besser der MS Compiler?
Wenn du bereit bist, einen Borland-Compiler zu verwenden, kann ich dir CodeGuard empfehlen.
Moritz
-
Hi,
erstma thx für die AntwortenDu baust für Debug Zwecke einen Überlauf in dein Programm ein? Nettes Hobby was du da hast.
Eigentlich baut man für Debug Zwecke Abfragen ein, ob ein Überlauf stattgefunden hat.Ähm ne so war das nicht gemeint
Der Array war da um Zwischenergebnisse zu überprüfen, und den hab ich einfach mal auf eine feste Grenze gesetzt, und gar nicht daran gedacht, dass da ein Überlauf stattfinden könnte.
Aktuelle MSC haben zB eine Option für "Buffer Security Checks". Mit der "Verschachtelung in structs" hat das übrigens nichts zu tun.
Stimmt der MSC Compiler gibt nie einen Error aus, wenn man einen festen Array überläuft, Compiler Option /Ge hab ich drin, trotzdem führt weder Lesen noch Schreiben über das Array hinaus zu einem Fehler, d.h.
int a[2], b; b=a[a]; a[2]=b;
Beides führt zu keiner Fehlermeldung beim Kompilieren, warum?
Borland? Naja, wenn schon umsteigen werden, dann wohl doch eher auf gcc - aber mal sehen.
Von Containerklassen hab ich in einem tut schon was gelesen, von Smart Pointern bis jetzt noch nicht - muss mich mal näher mit sowas beschäftigen, wenn ich wieder ein C++ Projekt anfange.
rabbit
-
RabbitsDad schrieb:
Stimmt der MSC Compiler gibt nie einen Error aus, wenn man einen festen Array überläuft
Hab mir mal das angeschaut. Offensichtlich wird da nur überprüft, ob die Rücksprungadresse überschrieben wird. Also was bei Hackerangriffen so beliebt ist. Eine generelle Buffer-Overrun Detektion hat man damit leider auch nicht.
RabbitsDad schrieb:
Compiler Option /Ge hab ich drin, trotzdem führt weder Lesen noch Schreiben über das Array hinaus zu einem Fehler
Seltsam, ich bekomm da zumindest ein
Run-Time Check Failure #2 - Stack around the variable 'foo' was corrupted.
RabbitsDad schrieb:
int a[2], b; b=a[a]; a[2]=b;
Beides führt zu keiner Fehlermeldung beim Kompilieren, warum?
Bei mir schon.
Liegt aber daran, dass der Code grundsätzlich falsch ist. Dass du keine Fehlermeldungen für Buffer-Overruns beim Kompilieren bekommst, sollte auch klar sein. Das ist kein MSC Problem, sondern liegt einfach daran, dass der Index ja erst zur Laufzeit feststeht. Und ich bin mir nicht sicher, ob es Compiler gibt, die zumindest Fehler bei Konstanten bringen, zB
int a[10]; a[10] = bla; // hier koennte man theoretisch einen Compiler Fehler bringen
btw:
"MSC Compiler" ist redundant - das hiesse ja praktisch Microsoft Compiler Compiler
-
RabbitsDad schrieb:
int a[2], b; b=a[a]; a[2]=b;
Beides führt zu keiner Fehlermeldung beim Kompilieren, warum?
Borland? Naja, wenn schon umsteigen werden, dann wohl doch eher auf gcc - aber mal sehen.
Einen GCC kann ich dir als Compiler nur empfehlen.
-
RabbitsDad schrieb:
Borland? Naja, wenn schon umsteigen werden, dann wohl doch eher auf gcc - aber mal sehen.
Mir ist, als hätten viele hier Vorurteile gegen Borland-Compiler. Warum? C++Builder kann ich halbwegs verstehen (weil er eine Anfängerfalle ist), aber hier geht es um den Compiler! Du mußt ja nicht den Builder, sondern nur den Compiler verwenden, und der ist
- schneller als MSVC und GCC (in Compilezeit)
- von MSVC und GCC am performantesten in der Codeerzeugung (jedenfalls bei meinen Programmen)
- kostenlosMoritz
-
audacia schrieb:
- kostenlos
Ist aber kein Unterschied zu den beiden anderen erwähnten Compilern.
-
valgrind ist das beste Tool, das ich in diesem Bereich kenne. Dieses läuft zur Zeit ausschließlich unter x86 Linux. Mitte des Jahres soll es auch auch auf AMD64 Linux laufen.
-
BoundsChecker ist besser.
-
Zu BoundsChecker finde ich im WWW nur Marketinggeschwätz. Gibt es eine Seite, die genau angibt, was dieses Werkzeug überprüft, und wie es das macht?
-
groovemaster schrieb:
int a[10]; a[10] = bla; // hier koennte man theoretisch einen Compiler Fehler bringen
meines wissens ist a ein pointer auf das erste element des arrays. wenn man nun schreibt 'a[10]' dann nimmt der compiler die adresse, welche in a gespeichert ist, zählt 10*sizeof(int) dazu, und greift auf das element an dieser stelle zu. das ist meiner ansicht nach absolut zulässig, wenn auch unangenehm (der speicher könnte ja schon belegt, und durch einen aufruf wie a[10] = bla; überschrieben werden). wie auch immer sehe ich keinen grund, warum der compiler an so einer stelle einen fehler ausgeben sollte. der programmierer WOLLTE es ja so.
-
audacia schrieb:
Mir ist, als hätten viele hier Vorurteile gegen Borland-Compiler. Warum? C++Builder kann ich halbwegs verstehen (weil er eine Anfängerfalle ist), aber hier geht es um den Compiler! Du mußt ja nicht den Builder, sondern nur den Compiler verwenden, und der ist
- schneller als MSVC und GCC (in Compilezeit)
- von MSVC und GCC am performantesten in der Codeerzeugung (jedenfalls bei meinen Programmen)
- kostenlosok, dann sage ich jetzt mal, dass bei mir der
- gcc in der compilezeit schneller ist als der bcc
- gcc auch sehr performanten code erzeugt
- gcc ebenfalls kostenlos ist.weiterhin
- gibt der bcc bei mit verbugte versionen von laufenden programmen aus (sprich: mit gcc kompiliert -> läuft; mit bcc kompiliert -> läuft nicht)
- baut bcc irgendwie grafik-bugs in der konsole ein, wo es todsicher ist, dass sie nicht auftreten dürften.außerdem hat doch jeder seinen compiler, den er gerne hat und dem er vertraut, nicht? aber das ganze soll ja nicht in eine compilerdiskussion ausarten
-
bcc ist der einzige Compiler, bei dem mir jemals ein Compilerbug aufgefallen ist (falscher Code). Und nicht nur einer. Die sind auch nicht so exotisch, dass sie eh nie auftreten. Ich ärgere mich regelmäßig damit herum.
Zur Speicher- und sonstiger Ressourcenverwaltung (im Zusammenhang mit Exceptions v.a.) kann ich nur ScopeGuard empfehlen.
-
Ringding schrieb:
bcc ist der einzige Compiler, bei dem mir jemals ein Compilerbug aufgefallen ist (falscher Code). Und nicht nur einer. Die sind auch nicht so exotisch, dass sie eh nie auftreten. Ich ärgere mich regelmäßig damit herum.
LOL, schon mal MSVC gesehen?
Außerdem, welche Version? Und worum geht es genau?
-
audacia schrieb:
Ringding schrieb:
bcc ist der einzige Compiler, bei dem mir jemals ein Compilerbug aufgefallen ist (falscher Code). Und nicht nur einer. Die sind auch nicht so exotisch, dass sie eh nie auftreten. Ich ärgere mich regelmäßig damit herum.
LOL, schon mal MSVC gesehen?
Außerdem, welche Version? Und worum geht es genau?deer neueste msvc hat kaum bugs.
-
savage_dog schrieb:
meines wissens ist a ein pointer auf das erste element des arrays
Nein, a ist kein Zeiger. a ist und bleibt ein Array.
savage_dog schrieb:
wenn man nun schreibt 'a[10]' dann nimmt der compiler die adresse, welche in a gespeichert ist, zählt 10*sizeof(int) dazu, und greift auf das element an dieser stelle zu. das ist meiner ansicht nach absolut zulässig
Erstens ist in a keine Adresse gespeichert, und zweitens sind nur Elementzugriffe von a[0] bis a[9] zulässig. Alles darüber hinaus erzeugt undefiniertes Verhalten.
savage_dog schrieb:
wie auch immer sehe ich keinen grund, warum der compiler an so einer stelle einen fehler ausgeben sollte
Den sehe ich schon. Der Typ ist zur compile-time bekannt (int[10]), und der Index ist eine Konstante (10). Ob es jetzt ein Fehler sein muss oder eine Warnung, darüber kann man streiten.
-
groovemaster schrieb:
zweitens sind nur Elementzugriffe von a[0] bis a[9] zulässig. Alles darüber hinaus erzeugt undefiniertes Verhalten.
siehe signatur...
im schlimmsten falle kann das ja zu systemabsturz führen.aber meiner meinung nach macht der compiler aus
a[10]
das hier:
*(a+10)