Unerklärlicher Segfault



  • Hallo!

    Ich habe hier einen Segfault, der mir völlig unerklärlich ist:

    dbl CComp::getSqArea() const
    {
      dbl ret(0);
    
      bla bla..
    
      cout<<"getSqArea returns "<<ret<<endl;
      return ret;
    }
    
    TestCode:
    
    ostream &operator<<(ostream &stream,  CComp& cc)
    {
      bla...
      cout<<"alive9"<<endl;
      stream<<cc.getSqArea()<<endl;
      cout<<"alive10"<<endl;
      bla...
    }
    
    CComp cc;
    bla...
    cout<<cc;
    

    Die Debug-Ausgabe lautet:

    alive9
    getSqArea returns 4.13009e+10
    4.13009e+10
    Segmentation fault
    

    Ich habe leider kein minimales, vollständiges Beispiel,
    in dem der Fehler auftritt. 'dbl' ist ein typedef auf einen
    genauen Datentyp, etwa double, aus einer Library (der aber
    hunderttausendfach getestet ist und wahrscheinlich nicht der
    Grund für den Ärger). Die Hoffnung ist, daß hier trotz der
    mangelhaften Beschreibung jemand einen Hinweis hat, wie der
    o.g. Code den Segfault auslösen könnte. Ich nehme an, daß
    da mit dem Stream irgendwas falsch läuft, denn wenn ich
    ersatzweise

    dbl sqArea=cc.getSqArea();
    cout<<"sqArea="<<sqArea<<endl;

    sage, macht das keine Probleme. Was übersehe ich?

    Danke, lg


  • Mod

    Mal einen Debugger benutzen?



  • SeppJ schrieb:

    Mal einen Debugger benutzen?

    Geht nicht. Der Datentyp ist mit Valgrind nicht kompatibel (Linux+GCC), und da das Problem erst nach vielen Stunden Rechenzeit auftritt, wäre Valgrind auch zu langsam.

    lg


  • Mod

    segfault1 schrieb:

    Geht nicht. Der Datentyp ist mit Valgrind nicht kompatibel (Linux+GCC), und da das Problem erst nach vielen Stunden Rechenzeit auftritt, wäre Valgrind auch zu langsam.

    1. WTF? Nicht kompatibel?
    2. Eigentlich dachte ich auch eher an einen normalen Debugger.
    3. Wenn es Stunden dauert will man es vielleicht trotzdem nicht im Debugger laufen haben. Dann hilft es, dass man im Absturzfall einen Coredump macht und diesen dann im Debugger lädt.
    4. Trotzdem kannste ja mal einen verkürzten Lauf mit valgrind machen.



  • SeppJ schrieb:

    segfault1 schrieb:

    Geht nicht. Der Datentyp ist mit Valgrind nicht kompatibel (Linux+GCC), und da das Problem erst nach vielen Stunden Rechenzeit auftritt, wäre Valgrind auch zu langsam.

    1. WTF? Nicht kompatibel?
    2. Eigentlich dachte ich auch eher an einen normalen Debugger.
    3. Wenn es Stunden dauert will man es vielleicht trotzdem nicht im Debugger laufen haben. Dann hilft es, dass man im Absturzfall einen Coredump macht und diesen dann im Debugger lädt.
    4. Trotzdem kannste ja mal einen verkürzten Lauf mit valgrind machen.

    Es handelt sich um einen Datentyp, der intern Fehlergrenzen mitrechnet und filtert, ob er exakt rechnen muß oder nicht. Da Valgrind bei der Rundung nicht wie echte Hardware vorgeht, läuft die Software in Valgrind nicht. Einen 'normalen' Debugger, also was anders als Valgrind, habe ich noch nie verwendet. Werd mich mal einlesen. Coredump hab ich auch noch nie gebraucht.

    Ich habe eigentlich gehofft, daß aus dem Code oben ersichtlich ist, daß da irgendeine Schweinerei passiert, die zum Absturz führt. Selbst sehe ichs leider nicht.

    lg


  • Mod

    segfault1 schrieb:

    Ich habe eigentlich gehofft, daß aus dem Code oben ersichtlich ist, daß da irgendeine Schweinerei passiert, die zum Absturz führt. Selbst sehe ichs leider nicht.

    Nützlich wäre der Ausgabeoperator von dbl. Aber probier vor allem mal den Debugger, dann siehst du wenigstens wo genau der Fehler auftritt.



  • Mit einiger Wahrscheinlichkeit hast du dir irgendwo in der Umgebung den Stack zerschossen. Gibt es in getSqArea möglicherweise einen Buffer, der etwas zu klein geraten ist? Vielleicht überschreibst du die Rücksprungadresse.



  • seldon schrieb:

    Mit einiger Wahrscheinlichkeit hast du dir irgendwo in der Umgebung den Stack zerschossen. Gibt es in getSqArea möglicherweise einen Buffer, der etwas zu klein geraten ist? Vielleicht überschreibst du die Rücksprungadresse.

    Hallo,

    danke für den Hinweis. Ich konnte das ganze nun mit einem anderen Datentyp und
    einem kleinen Datensatz in Valgrind laufen lassen und es gibt tatsächlich einen
    Memory-Bug. Zwar um einiges früher, aber wahrscheinlich trotzdem genau damit
    in Zusammenhang. 👍

    lg



  • Fehlt da ein "return *this;" beim opeartor<< ?
    Ich kann das dem "..." leider nicht ansehen (hint hint).



  • krümelkacker schrieb:

    Fehlt da ein "return *this;" beim opeartor<< ?
    Ich kann das dem "..." leider nicht ansehen (hint hint).

    return stream; meinst Du. Ist hinten dran. Ich bin grade dabei, den Bug zu korrigieren. Ich habe von einem leeren Vektor v den Iterator v.begin() dereferenziert. Da zuvor dort ein Objekt drinlag, ist das nicht weiter aufgefallen. War zusätzlich schwer zu finden, weil eine ordentliche Distanz zur Auswirkung bestand. Ich hoffe jedenfalls, daß es das dann war. Mal sehen...

    lg


Anmelden zum Antworten