n' format specifier disabled (bei printf)
-
Guten Abend,
Ich schreibe gerade ein Programm das eine Verbindung zu einem Server im Internet herstellt und Quellcodes von Webseiten downloaden und analysieren soll. Um den erhaltenen HTML-Code über die Standardaugabe anzuzeigen bzw. zu speichern benutze ich die Funktion printf().
Das Programm bis jetzt bei einer einzigen Webseite die ich fand: http://www.mathematik.uni-ulm.de/sai/ss02/soft/blatt7/http.html . Sie ist... etwas schlicht. ^^
Bei komplexen Seiten wie Wikipedia scheitert das Programm. Ich bekomme eine 4xx Fehlermeldung. Das schlimme ist daran, dass die gelierferten Daten diese Format Spezifizierer enthalten. Während des Ausführens taucht also folgender Fehlerdialog auf:
Microsoft Visual C++ Debug Library
Debug Assertion Failed!
....
Expression("n' spezifier disabled', 0)
....Soweit ich das gelesen hab kann es ein Sicherheitsrisiko sein diese Format Spezifizierer zuzulassen. Jetzt wollte ich von euch wissen:
- Ist das wirklich ein Sicherheitsrisiko?
- Was ist die einfachste Alternative zu printf() um die Daten anzuzeigen/zu speichern?
Im Endeffekt will ich die Daten ja noch nicht mal speicher/anzeigen, sondern nur nach bestimmten Mustern parsen.
- Wäre es dazu sinnvoll den mehrmals gefüllten Buffer zu einer Zeichenkette zusammenzuhängen in der ich dann suchen kann?
- Vielleicht weiß jemand wie Browser mit diesen Spezifizierern im Quellcode umgehen?
MfG Tobi.
-
Wenn ich das richtig lese, geht es dabei nicht um irgendwelche Teile der HTML-Daten, sondern darum, dass der verarbeitende Code %n in einem printf-Format-String benutzt. Mit dem kann man die Anzahl der bisher ausgegebenen Zeichen speichern; inwiefern das ein Sicherheitsrisiko ist, ist für ich allerdings nicht direkt offensichtlich. Welche Gründe gab denn die Quelle, die das als Sicherheitsrisiko bezeichnete?
Wie dem auch sei, in C++ ist es üblich, Ausgaben über Stream-Objekte zu betreiben. Im Fall von Konsolenausgaben ist das meistens std::cout, etwa
#include <iostream> int main() { std::cout << "Hallo, Welt!" << std::endl; }Beim Parsen hilft dir das aber natürlich herzlich wenig. Je nach Komplexität des Parsers bieten sich mehrere Möglichkeiten an; ich an deiner Stelle würde mich in den Boost-Bibliotheken umsehen, speziell Boost.Regex, Boost.Xpressive und Boost.Spirit.
-
Hier ist der Artikel mit der Überschrift "Do Not Use the "%n" Format String Specifier": https://buildsecurityin.us-cert.gov/bsi/articles/knowledge/guidelines/340-BSI.html
Aber wenn das nicht riskant ist, lasse ich die einfach zu.
Eigentlich möchte ich möglichst wenige Bibliotheken einbauen. Für mich kamen zwei Möglichkeiten in Frage:
1. Die Inhalte des Buffers aneinanderhängen und darin suchen.
2. Die Inhalte in eine Textdatei speichern mit der ich arbeite. Aber so groß sind HTML-Dateien ja eigentlich nicht.
-
printf("%s", buffer);
-
Ich bin verblüfft...
Ich dachte erst "Schon klar. Ich weiß was Formatspezifizierer wie %d und %s sind...". Aber genau dieses kurze Kommando rettet meinen Code.

Bisher hatte ich zur Ausgabe printf(recvData) benutzt.
Danke!
-
In C++ nutzt man dafür std::cout. Damit wäre der Fehler gar nicht aufgetreten.