Herzlich Willkommen, lieber Gast!
  Sie befinden sich hier:

  Forum » C / C++ (ANSI-Standard) » Stackoverflow erkennen

Forum | Hilfe | Team | Links | Impressum | > Suche < | Mitglieder | Registrieren | Einloggen
  Quicklinks: MSDN-Online || STL || clib Reference Grundlagen || Literatur || E-Books || Zubehör || > F.A.Q. < || Downloads   

Autor Thread - Seiten: > 1 < [ 2 ] [ 3 ] [ 4 ]
000
09.06.2005, 14:23 Uhr
Arta



Hallo,

ich habe folgendes Problem:
Ich möchte mit Hilfe von Signalhandlern verschiedene Signale abfangen, um dann spezifisch darauf zu reagieren. Unter diesen Signalen befinden sich auch die Signale SIGSEGV und SIGBUS, also Signale, die potentiell durch einen Stackoverflow versursacht wurden.
Mein Ziel ist es nun, im Signalhandler abzufragen, ob die Ursache der Signale eben solch ein Stackoverflow war(dann will ich den ganzen Prozess beenden) oder ob dies einen anderen Grund hat (vielleicht hat ja irgendwer von irgendwo einfach einen SIGSEGV an den Prozess geschickt oder es hat einen anderen grund etc.), damit ich dann möglicherweise im Programm an einer definierten Stelle weitermachen kann.
Das ganze möchte ich sowohl unter Solaris auf einem Sparc, als auch unter Linux auf einem Intel zum laufen kriegen.
Auf Solaris ist das auch gut möglich gewesen:
1. aus dem ucontext den ss_sp-Zeiger auslesen: Der Zeigt auf die niedrigstmögliche Stackadresse
2. aus dem ucontext das Register ESP auslesen: Der Stackpointer
Nun kann man einfach abfragen ob die Stackpointeradresse unter der Adresse des ss_sp-Zeigers liegt und wenn ja, dann hat man einen Stackoverflow erkannt.

Unter Linux auf einem Intel ergeben sich nun für mich aber sehr seltsame ergebnisse:
- Der Stackoverflow wird nach wie vor korrekt gemeldet (bei Standarteinstellungen, sobald der ESP-Zeiger die ersten 8MB hinter sich gelassen hat...)
- Der SS_SP-Zeiger zeigt eifnach immer irgendwo hin, aber nicht an eine feste Stelle, die den niedrigst mögliche Stackadresse darstellt.
- Die Stacksize, die ich mir über den ucontext (oder auch über pthread) besorge, wird immer mit 1 GB, anstatt mit 8MB angezeigt, wobei 8MB bei mir aber der korrekte Wert ist.

Hat vielleicht jemand eine Ahnung, oder einen weiteren Tipp wie ich mir unter C++ auf Linux/Intel die korrekte Stackgrösse etc. holen kann, oder warum die Stacksize immer mit 1GB angegeben wird und der SS_SP-Zeiger vom ucontext keinen festen Wert hat?

Gruss
Arta
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
001
09.06.2005, 15:21 Uhr
virtual
Sexiest Bit alive
(Operator)


SIGSEGVs oder SIGBUS fangen zu wollen ist ungefähr genauso, erst ein Brett ansägen zu lassen und sich dann drauf zu stellen: wenn ein Programm einen Stackoverflow hat, dann wird es normalerweise sterben. Du hast in diesem Fall einen core und kannst mit einem entsprechenden Debugger eine gute Portmortem Analyse machen.

oder anders ausgedrückt: ein Programm welches eine Stackoverflow hat ist exakt genauso fehlerhaft wie ein Programm, welches einen NULL Pointer dereferenziert. Bring Deinen Source in ordnung, dann brauchst Du auch keine unsicheren Tricksereien zu machen.
--
Gruß, virtual
Quote of the Month
Ich eß' nur was ein Gesicht hat (Creme 21)
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
002
09.06.2005, 15:57 Uhr
Arta



Wie ich oben geschrieben habe, soll im Signalhandler im Falle eines Stackoverflows das Programm auch beendet werden.... - ich hab nicht vor dann weiterzumachen und gleich wieder im Signalhandler zu landen
Und den Signalhandler selbst wird ein Overflow aufgrund eines Signalstacks erstmal recht wenig stören.

Das Signal kann aber auch gesendet werden, ohne das ein Stackoverflow vorliegt - und deshalb das Problem oben - ob das im "normalfall" sinn macht, is ja gar nich die Frage...

Wenn sich dann herausstellt, dass das Fangen nicht das erwünschte Resultat bringt und ich damit gar nichtsmehr anfangen kann(wovon ich im moment nicht ausgehe), würde mich die Stackfrage allgemein trotzdem noch interessieren....

Sprich: für weitere Tipps, die mich da vielleicht weiterbringen wäre ich dankbar.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
003
09.06.2005, 16:36 Uhr
Guybrush Threepwood
Gefürchteter Pirat
(Operator)


Was virtual damit sagen wollte ist das du lieber die Ursache des Stack Overflows finden und korrigieren sollst anstatt so ein gewurschtel zu verursachen.

Der kommt ja nicht von ungefähr und kann je nach BS einiges beim Benutzer anrichten...
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
004
07.11.2005, 13:26 Uhr
~Sponge
Gast


Hallo liebe leutz.. zufällig bin ich hier grad draufgestossen, etwas spät aber immerhin. Also ich habe ein ähnliches Problem wie Arta, ich muss ebenfalls auf einen Overflow reagieren, bzw. ihn eigentlich voraussehen, um dann mit einer entsprechenden LogMeldung und dem Ende des Programms zu reagieren. Sicherlich sollte man die Ursache des Stackoverflows beseitigen, nur ist dies manchmal einfach nicht möglich, weil man nicht alle äußeren Umstände kennt. So handelt es sich bei mir um eine mathematische Berechnung, die doppelt rekursiv ist und in jedem Rekursionschritt wiederrum eine Rekursion startet. Da nun die Tiefe der Rekusion nur von dem gestellten Problem abhängt und dieses mittels einen FileInputs gegeben wird (es handelt sich um Splineberechnungen), kann ich einfach nicht sagen ob und wann ein StackOverflow auftritt.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
005
07.11.2005, 14:11 Uhr
ao

(Operator)


Hallo Sponge,
es gibt keine ANSI-C-Standardlösung dafür, aber vielleicht eine compiler-spezifische. Welcher Compiler ist das?

ao
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
006
07.11.2005, 16:27 Uhr
~Sponge
Gast


Man so schnell hätte ich garned mit einer Antwort gerechnet..
ich benutze den GCC Compiler Version 3.4.2 (MINGW Edition)
Hatte überlegt einfach ein StackLimit zu setzen und das dann durch den GCC mit der Option fno-stack-limit mir einfach ein Limit zu setzen bzw. die evtl einfachere Variante ist -fstack-check, ich bin mir aber nicht sicher ob windows merkt, dass ein Stackoverflow stattgefunden hat.... ok habe es gerade probiert.. zumindest win2k scheint dies nicht festzustellen.. das scheint wohl noch ein bissl recherche und experimente zu erfordern
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
007
07.11.2005, 21:52 Uhr
ao

(Operator)



Zitat von ~Sponge:
ich benutze den GCC Compiler Version 3.4.2 (MINGW Edition)

Dann schau doch mal, ob es in deiner libc eine Funktion stackavail oder so ähnlich gibt, so wie in der djgpp-Implementierung hier: www.delorie.com/djgpp/doc/libc/libc_743.html

ao
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
008
09.11.2005, 10:57 Uhr
~Sponge
Gast


Ich habe das Problem jetzt etwas anders gelöst.. als ich drauf kam wie hab ich mir erstmal den Kopf gegen die Wand gehauen, weil es einen ja fast beisst.
Ich kann ja einfach die Adressen der lokalen Variablen hernehmen und habe damit die aktuellen Speicheradressen des Stacks.. ist etwas umständlich, aber auf jeden Fall funktionsfähig.
Nun hab ich aber gleich an neues Problem ... nun bin ich zwar in der Lage die größe des Stacks in etwa zu bestimmen, aber ich habe keine Ahnung wie eine DLL mit dem Stack arbeitet. Wenn ich eine DLL aufrufe, wird der Stack der DLL auf meinen eigenen draufgepackt oder hat sie ihren eigenen? Ich denke ersteres macht mehr Sinn, bin mir aber nicht sicher.
Das Problem dabei ist, dass mein Programm als DLL kompiliert wird und somit meine Rekursionstiefe ganz entscheidend vom aufrufenden Programm und deswegen Stack abhängen würden.

Ich danke demjenigen der diese Frage oder einen Tip in der Hinsicht für mich hat schon mal im Voraus.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
009
09.11.2005, 11:13 Uhr
Tommix



Hallo,
die Größe des Stacks wird vom rufenden Programm bestimmt. Ich bin selbst schon mal drauf reingefallen. Ich habe seinezeit allerdings kein vernünftiges Workaround gefunden und die betroffene Funktion letztendlich noch mal neu implementiert (ohne Rekursion).

Gruß, Tommix


Bearbeitung:

Das war jetzt auf Windows bezogen und von daher womöglich fehl am Platz (von wegen SIGSEV und so).


Dieser Post wurde am 09.11.2005 um 11:15 Uhr von Tommix editiert.
 
Profil || Private Message || Suche Download || Zitatantwort || Editieren || Löschen || IP
Seiten: > 1 < [ 2 ] [ 3 ] [ 4 ]     [ C / C++ (ANSI-Standard) ]  


ThWBoard 2.73 FloSoft-Edition
© by Paul Baecher & Felix Gonschorek (www.thwboard.de)

Anpassungen des Forums
© by Flo-Soft (www.flo-soft.de)

Sie sind Besucher: