Frage zum Pufferüberlauf



  • Ich sehe das doch richtig, dass str1 eigentlich viel zu gross für str2 ist oder? Aber wieso schmiert das Programm nicht ab, wenn ich noch ein Zeichen mehr reinschreibe?



  • Dafür gibt es keine Erklärung, du erzeugst damit undefiniertes Verhalten und wie dieser Begriff schon vermuten lässt, kann man hier nicht voraussagen was passieren wird.
    Könnte 99mal gut gehen und beim 100. mal macht es PENG!



  • Das liegt aber wohl eher am Compiler! oder?
    Was nutzt du für einen?
    Compiliertes Programm in der Konsole (bash) ausgeführt -> Speicherzugriffsfehler.
    gcc-Version 3.3.4 20040623



  • JKL schrieb:

    Das liegt aber wohl eher am Compiler! oder?

    Das liegt hauptsächlich an den Daten die im Stack folgen.

    int main()
    {
    	const char* c = "aaaaa";
    	int i = 0;
    	char b[2];
    	strcpy(b, c);
    	assert(i == 0);
    }
    

    Hier stehen die Chancen nicht schlecht, dass der Teilstring "aaa" in den Speicherbereich von i geschrieben werden. Da dieser Speicher dir gehört, kann es durchaus sein, dass du keinen Speicherzugriffsfehler erhälst.

    Aber wie bereits gesagt wurde: Das Verhalten ist undefiniert. Und statt sich den Kopf darüber zu zerbrechen, was mit welchem Compiler unter welchen Umständen und bei welcher Wetterlage passiert, sollte man lieber das Programm korrigieren.



  • Ich verstehe nicht warum so etwas in C++ möglich ist.
    Man sollte doch denken C++ ist eine moderne Sprache.
    Es ist eine Typstrenge Sprache. Konvertieren folgt nur nach bestimmten Regeln.
    Doch wenn es um solche (auch) gravierenden Sachen geht dann ist es hin.
    So etwas MUSS mit einer Fehlermeldung vom Compiler abgebrochen werden.
    Da c ja schon initialisiert ist mit einem zu hohem Wert ist ja bekannt das es ein Fehler ist, der reservierte Speicherplatz reicht nicht aus.
    Man kann keine "double Wert" in einen int Bereich setzen -> Fehler.
    Aber man kann einem vordefinierten 4 Byte Bereich einfach mal so 20 Byte zuteilen ohne das es einem auffällt.
    Wenn c nicht initialisiert ist dann sieht die Sache schon anders aus.
    Aber in diesem Fall ist das ein Designfehler von C++, das ist zumindest meine Meinung.

    Das der Compiler das auch noch compiliert ist für mich sowieso völlig unverständlich.



  • Dass sowas von einem unregistrierten Benutzer kommen wuerde, war mir schon fast
    klar. Versuch es einfach gar nicht zu verstehen.

    Unglaublich, meine Postings werden in letzter Zeit so aggressiv, woran das wohl
    liegen mag?

    mfg
    v R



  • Buffer schrieb:

    Ich verstehe nicht warum so etwas in C++ möglich ist.
    [...]
    Das der Compiler das auch noch compiliert ist für mich sowieso völlig unverständlich.

    So etwas noch zur Compilezeit zu erkennen ist sehr schwer und würde auch die Compilierzeit _vervielfachen_ und eine Prüfung von Buffer overflows zur Laufzeit wirkt sich negativ auf die Geschwindigkeit des Programms aus. Aber wird nicht, wenn man ein Programm debuggt in jedem Fall bei einem Bufferoverflow abgebrochen? Bin mir nicht sicher, aber ich dachte das wäre, zumindest bei den meisten debuggern, so.

    Man kann keine "double Wert" in einen int Bereich setzen -> Fehler.

    double blubb = 1;
    int i = static_cast<double>(blubb);
    

    😕



  • C++ ist vom Design her auf Schnelligkeit und Effizienz ausgelegt.
    Wenn man "alles" überprüfen müsste dann wäre es nicht möglich schnelle und effiziente Programme zu schreiben.
    Wer C++ Programmieren lernen will der sollte sich schon mit den Tücken der Sprache auseinandersetzen. Man kann keine Sprache dafür verantwortlich machen das man sich selber Sicherheitslücken programmiert oder anders fehlerhafte Programme schreibt.
    Obwohl die Aussage an sich nicht ganz unrichtig ist bin ich mir nicht sicher ob es dennoch nur ein Trollpost gewesen ist. Trotz alle dem, lerne die Sprache "richtig" oder lerne was anderes!

    @Realisticer

    Dass sowas von einem unregistrierten Benutzer kommen wuerde, war mir schon fast
    klar. Versuch es einfach gar nicht zu verstehen.

    Unglaublich, meine Postings werden in letzter Zeit so aggressiv, woran das wohl
    liegen mag?

    Weil du ein aggresiver Mensch bist der zwar nichts entgegensetzen kann an einer Aussage aber dennoch mal was posten will?

    @godlikebot

    double blubb = 1;
    int i = static_cast<double>(blubb);
    

    Ist hier also ein double Wert == int Wert ?
    Cast = konvertiert.
    Typstrenge:

    double blubb = 1;
    int i = blubb;
    

    Wenn man das "castet" ..... !



  • Weil du ein aggresiver Mensch bist der zwar nichts entgegensetzen kann an einer Aussage aber dennoch mal was posten will?

    Oder vielleicht, weil man diese Postings 1000x und mehr schon gelesen hat und
    einem irgendwann mal das ganze bis zum Hals steht?

    Ich ueberlasse es dir, mich dahingehend zu bewerten.

    mfg
    v R



  • Obwohl die Aussage an sich nicht ganz unrichtig ist bin ich mir nicht sicher ob es dennoch nur ein Trollpost gewesen ist

    Da hast du "Troll" missverstanden. Hier stellt jemand ne Frage, ganz offensichtlich ernst. Kein Grund die Troll-Keule auszupacken.



  • godlikebot schrieb:

    Aber wird nicht, wenn man ein Programm debuggt in jedem Fall bei einem Bufferoverflow abgebrochen? Bin mir nicht sicher, aber ich dachte das wäre, zumindest bei den meisten debuggern, so.

    Nein nein, da hilft nur std::vector nehmen und den op[] h4x0rn, so dass er eine Indexprüfung vornimmt.
    Ein gewöhnliches C-Array (wie der Name schon sagt, ist es leicht aus der Mode) macht eigentlich überhaupt keinen Sinn mehr, ab und zu vielleicht ein boost::array wo man ja auch leicht ein assert einbaun kann.
    Das kostet dann im Release-build nichts, man hat trotzdem eine größere Sicherheit nach einigen Tests und man hat ein anständiges Objekt, mit dem man hantieren kann.

    Heapdoktor schrieb:

    Wenn man "alles" überprüfen müsste dann wäre es nicht möglich schnelle und effiziente Programme zu schreiben.

    Das ist auch nicht ganz richtig. Mit solchen Ersparnissen kannst du nur noch das letzte bisschen rauskratzen, das würde ich jetzt nicht überbewerten.



  • Heapdoktor schrieb:

    @godlikebot

    double blubb = 1;
    int i = static_cast<double>(blubb);
    

    Ist hier also ein double Wert == int Wert ?
    Cast = konvertiert.
    Typstrenge:

    double blubb = 1;
    int i = blubb;
    

    Wenn man das "castet" ..... !

    Ja, sorry... Denkfehler meinerseits 🙂



  • Obwohl die Aussage an sich nicht ganz unrichtig ist bin ich mir nicht sicher ob es dennoch nur ein Trollpost gewesen ist

    Da hast du "Troll" missverstanden. Hier stellt jemand ne Frage, ganz offensichtlich ernst. Kein Grund die Troll-Keule auszupacken.

    <missverständnis>So war das nicht gemeint, der Fragesteller ist hier außen vor.
    Ich meinte Buffer damit, ich bin mir nicht sicher warum er das geschrieben hat.
    Wollte er trollen oder nicht? Ist auch egal. Auf jeden Fall ist es so -> es passte nicht zum Thema.
    Ich wollte den Threadersteller auf keinen Fall unterstellen hier rum zu trollen, die Frage klar und eindeutig kein Trollpost.</missverständnis>

    @Optimizer

    Wenn man "alles" überprüfen müsste dann wäre es nicht möglich schnelle und effiziente Programme zu schreiben.

    Das ist auch nicht ganz richtig. Mit solchen Ersparnissen kannst du nur noch das letzte bisschen rauskratzen, das würde ich jetzt nicht überbewerten.

    Das war die Vorstellung von den Leuten die C++ zu dem gemacht haben was es heute ist, ob es Sinn macht oder nicht ....... Thema wo keiner Recht bekommt.

    Aussage (kein Zitat) von Breymann, Ulrich Prof. Dr. in seinem Buch über C++
    Es geht um Vektoren

    Es gibt keine Bereichsüberprüfung der Bereichsüber- oder -unterschreitung! Zugriffe auf nicht existierende Elemente wie c = v[100] erzeugen keine Fehlermeldung, weder durch Compiler noch ........

    ...... Grund: Schnelligkeit ist ein Designprinzip ........
    ... Überprüfung kostet Zeit.

    Umgehen der Falle

    cout << v.at(1000) << endl; // (10 max.) Programmabbruch mit Fehlermeldung

    In so fern hatte Buffer nicht ganz unrecht. Aber dazu keine Diskussion mehr.

    Frohe Arbeitswoche noch! 😋


Anmelden zum Antworten