Kann ich mich gegen SQL Injection schützen, indem Sie einzelne Anführungszeichen und umgebende Benutzereingaben in einfache Anführungszeichen setzen?
Merke ich, dass parametrisierte SQL-Abfragen ist der optimale Weg zur Bereinigung von Benutzereingaben beim erstellen von Abfragen mit Benutzereingaben, aber ich Frage mich, was ist falsch mit der Einnahme von Benutzereingaben und Flucht jeder einzelne Zitate und um die ganze Zeichenfolge in einfache Anführungszeichen. Hier ist der code:
sSanitizedInput = "'" & Replace(sInput, "'", "''") & "'"
Einzelne zitieren, den der Benutzer eingibt, wird ersetzt mit Doppel-single-Angebote, die eliminiert die Fähigkeit der Benutzer, um das Ende der Zeichenfolge, alles sonst könnte es für Sie geben, wie Semikolons, Prozent-Zeichen, etc, all das wird Teil der Zeichenfolge und nicht tatsächlich ausgeführt, die als Teil des Befehls. Wir sind Microsoft SQL Server 2000 verwenden, für die ich glaube, dass die single-quote ist die einzige string-Trennzeichen, und der einzige Weg zu entkommen die Zeichenfolge, Trennzeichen, so gibt es keinen Weg, um auszuführen alles, was der Benutzer eingibt.
Sehe ich keinen Weg, der zum starten einer SQL-injection-Angriff gegen diese, aber ich merke, dass wenn dies so kugelsicher, wie es mir scheint, jemand anderes hätte es schon und es wäre gängige Praxis. Meine Frage ist: was ist falsch an diesem code? Weiß jemand einen Weg, um eine SQL-injection-Angriff in der Vergangenheit dieser Bereinigung Technik? Beispiel Benutzereingaben, die nutzt diese Technik sehr hilfreich wäre.
UPDATE:
Vielen Dank an alle für Ihre Antworten; so ziemlich alle Informationen, die ich stieß bei meiner recherche zeigte sich auf dieser Seite irgendwo, das ist ein Zeichen der Intelligenz und Geschicklichkeit der Menschen, die sich Zeit genommen, Ihre arbeitsreiche Tage, um mir zu helfen mit dieser Frage.
Den Grund habe ich noch nicht angenommen, keine der Antworten ist, dass ich immer noch weiß nicht jeder Weg, um effektiv zu starten Sie einen SQL-injection-Angriff gegen diesen code. Ein paar Leute vorgeschlagen, dass ein backslash würde ausbrechen einfache Anführungszeichen und belassen Sie das andere Ende der Schnur so, dass der rest der Zeichenfolge ausgeführt werden würde als Teil der SQL-Befehl, und ich merke, dass diese Methode funktionieren würde, um zu injizieren SQL in eine mySQL-Datenbank, sondern in der MS SQL 2000 die einzige Möglichkeit (die ich habe finden können) auf der Flucht ein single-quote mit einem weiteren single-Fans aufgepasst; Schrägstriche werden es nicht tun. Und es sei denn, es gibt einen Weg zu stoppen die Flucht der single-quote, keiner der rest von der Benutzereingabe ausgeführt werden, weil es alle als einen zusammenhängenden string.
Ich verstehe, dass es bessere Möglichkeiten gibt zu desinfizieren input, aber ich bin wirklich mehr daran interessiert zu lernen, warum die Methode, die ich oben angegeben nicht funktionieren. Wenn jemand weiß, von irgendeiner spezifischen Weise zum bereitstellen eines SQL-injection-Angriff gegen diese Bereinigung Methode, die ich lieben würde, um es zu sehen.
InformationsquelleAutor der Frage Patrick | 2008-09-26
Du musst angemeldet sein, um einen Kommentar abzugeben.
Erste von allen, es ist nur eine schlechte Praxis. Input-Validierung ist immer notwendig, aber es ist auch immer fraglich.
Schlimmer noch, blacklist Validierung ist immer problematisch, es ist viel besser, explizit und genau definiert, welche Werte/Formate Sie akzeptieren. Zugegeben, das ist nicht immer möglich - aber bis zu einem gewissen Ausmaß, es muss immer gemacht werden.
Einige Forschungsarbeiten auf dem Thema:
Punkt ist, jeder blacklist, die Sie tun (und allzu freizügige whitelists) kann umgangen werden. Der Letzte link zu meinem Papier zeigt Situationen, in denen sogar zitieren, der Flucht umgangen werden können.
Selbst wenn diese Situationen nicht auf Sie zutreffen, ist es immer noch eine schlechte Idee. Darüber hinaus, es sei denn, Ihre app ist trivial klein, du gehst zu haben, um mit der Wartung, und vielleicht eine gewisse governance: wie stellen Sie sicher, dass Ihre getan Recht, überall, die ganze Zeit?
Dem richtigen Weg, es zu tun:
InformationsquelleAutor der Antwort AviD
Okay, diese Antwort bezieht sich auf die Aktualisierung der Frage:
Nun, neben der MySQL-backslash Flucht - und unter Berücksichtigung, dass wir reden eigentlich über MSSQL, es gibt eigentlich 3 Möglichkeiten, noch SQL-Injektion Ihren code
Berücksichtigt werden, dass diese nicht alle zu allen Zeiten gültig, und sind sehr abhängig von Ihrem code um ihn herum:
Dann, was Sie bekommen - ist der Benutzername, der entkam, und dann gekürzt auf 20 Zeichen. Das problem hier - ich halte mein Angebot im 20-Zeichen (z.B. nach 19, a), und Ihre Flucht Zitat gekürzt werden (in the 21st Charakter). Dann die SQL
kombiniert mit den oben erwähnten fehlerhaften Benutzername wird im Ergebnis das Passwort bereits außerhalb die Anführungszeichen, und wird nur die payload direkt ein.
3. Unicode-Schmuggel - In bestimmten Situationen ist es möglich, übergeben eine high-level-unicode-Zeichen, die sieht wie ein Zitat, aber nicht - bis es zu der Datenbank, wo plötzlich es ist. Denn es ist nicht ein Angebot, wenn Sie es prüfen, es geht durch leichte... Siehe meine Vorherige Antwort für weitere details und link zum original-Forschung.
InformationsquelleAutor der Antwort AviD
Kurz gesagt: tun Sie Nie-Abfrage Flucht selbst. Sie sind verpflichtet, etwas zu bekommen falsch. Stattdessen verwenden Sie parametrisierte Abfragen, oder wenn Sie nicht tun können, dass aus irgendeinem Grund, verwenden Sie eine vorhandene Bibliothek, die das für Sie übernimmt. Es gibt keinen Grund, es zu tun selbst.
InformationsquelleAutor der Antwort Nick Johnson
Ich weiß, das ist eine lange Zeit, nachdem die Frage gestellt wurde, aber ..
Eins Weg, um einen Angriff auf den 'zitieren, der das argument" - Verfahren ist mit dem abschneiden der Zeichenfolge.
Laut MSDN, SQL Server 2000 SP4 (und SQL Server 2005 SP1), wird eine zu lange Zeichenkette wird ruhig abgeschnitten.
Wenn Sie zitieren, eine Zeichenfolge, die string-Größe erhöht. Jedes Apostroph ist wiederholt.
Diese können dann verwendet werden, um push-Teil der SQL-außerhalb des Puffers. So könnte man effektiv trimmen entfernt Teile einer where-Klausel.
Wäre dies wohl meist sinnvoll, in einem 'user-admin' Seite Szenario, wo Sie missbrauchen könnte die 'update' - Anweisung nicht alle Prüfungen vor, die es tun sollte.
Also, wenn Sie sich entscheiden, zu zitieren, alle Argumente, stellen Sie sicher, Sie wissen, was geht auf, die mit der Zeichenfolge Größen und sehen zu, dass Sie es gar nicht abschneiden.
Ich würde empfehlen, geht mit Parametern. Immer. Wünschte, ich könnte erzwingen, dass in der Datenbank. Und als Nebeneffekt, sind Sie eher, um besser zu werden cache-hits, da mehr Aussagen gleich Aussehen. (Dies war sicher auch auf Oracle 8)
InformationsquelleAutor der Antwort Jørn Jensen
Eingang Hygiene ist nicht etwas, was Sie wollen, half-ass. Verwenden Sie Ihren ganzen Arsch. Verwenden Sie reguläre Ausdrücke auf text-Felder. TryCast Ihre Numerik an der richtigen numerischen Typ, und melden eines Fehlers, wenn es nicht funktioniert. Es ist sehr einfach, nach solchen mustern in Ihrer Eingabe, wie"--. Davon, dass alle Eingaben vom Benutzer feindlich.
InformationsquelleAutor der Antwort tom.dietrich
Habe ich verwendet diese Technik beim Umgang mit der "erweiterten Suche" Funktion, wo der Bau einer Abfrage von Grund auf neu war die einzige brauchbare Antwort. (Beispiel: ermöglichen dem Benutzer die Suche nach Produkten, basierend auf eine unbegrenzte Menge von Einschränkungen auf Produkt-Attribute, die Anzeige von Spalten und Ihre zulässigen Werte als GUI-controls zur Verringerung der Lern-Schwelle für den Anwender.)
In sich selbst, es ist sicher, soweit ich weiß. Wie die anderen Beantworter der Frage darauf hingewiesen, Sie können jedoch auch die Notwendigkeit einer Auseinandersetzung mit backspace entkommen (wenn auch nicht bei der übergabe der Abfrage an SQL Server über ADO oder ADO.NET zumindest -- kann nicht verbürgen für alle Datenbanken oder Technologien).
Der Haken ist, dass Sie wirklich haben, um sicher zu sein, welche Zeichenfolgen enthalten, die Benutzer-Eingabe (immer potentiell schädliche), und die Zeichenfolgen sind gültige SQL-Abfragen. Eine der fallen ist, wenn Sie Werte aus der Datenbank -- waren diese Werte ursprünglich vom Benutzer geliefert? Wenn dem so ist, müssen Sie auch entkommen. Meine Antwort ist, zu versuchen zu bereinigen, so spät wie möglich (aber nicht später!), bei der Konstruktion der SQL-Abfrage.
Jedoch in den meisten Fällen, die parameter verbindlich ist der Weg zu gehen-es ist nur einfacher.
InformationsquelleAutor der Antwort Pontus Gagge
Dass es eine schlechte Idee auf jeden Fall, wie Sie zu wissen scheinen.
Was über so etwas wie Flucht vor der quote in Zeichenfolge wie diese: \'
Ihre ersetzen führen würde: \"
Wenn Sie die backslash-escapes das erste Zitat, dann das zweite Anführungszeichen beendet den string.
InformationsquelleAutor der Antwort WW.
Einfache Antwort: Es funktioniert manchmal, aber nicht immer.
Sie möchten, verwenden Sie weiße-Liste-überprüfung auf alles Sie tun, aber ich weiß, das ist nicht immer möglich, so dass Sie gezwungen sind, gehen mit der besten Vermutung blacklist. Ebenso, das Sie verwenden möchten parametrisierten gespeicherten Prozeduren in alles, aber noch einmal, das ist nicht immer möglich, so dass Sie gezwungen sind, verwenden Sie sp_execute mit Parametern.
Es gibt Möglichkeiten, um jede nutzbare blacklist, die Sie mit oben kommen kann (und einige whitelists).
Einen anständigen Kommentar ist hier: http://www.owasp.org/index.php/Top_10_2007-A2
Wenn Sie brauchen, um dies zu tun, wie eine schnelle Lösung, um Ihnen Zeit zu bekommen, ein echtes in Ort, es zu tun. Aber glaube nicht, dass du sicher bist.
InformationsquelleAutor der Antwort
Gibt es zwei Möglichkeiten, es zu tun, es gibt keine Ausnahmen, sicher vor SQL-Injektionen; prepared statements oder prameterized gespeicherte Prozeduren.
InformationsquelleAutor der Antwort olle
Wenn Sie parametrieren Abfragen zur Verfügung, Sie sollten mit Ihnen zu allen Zeiten. Alles was es braucht ist eine Abfrage, um gleiten durch das Netz und die DB ist in Gefahr.
InformationsquelleAutor der Antwort Kev
Ja, das sollte funktionieren, bis jemand läuft SET QUOTED_IDENTIFIER OFF und verwendet ein doppeltes Anführungszeichen auf Sie.
Edit: Es ist nicht so einfach wie nicht so dass der böswillige Benutzer zu deaktivieren Bezeichner:
Es gibt eine Menge von Möglichkeiten, QUOTED_IDENTIFIER, könnte ausgeschaltet werden, ohne Sie unbedingt zu kennen. Zugegeben - das ist nicht die smoking gun ausnutzen, die Sie suchen, aber es ist eine ziemlich große Angriffsfläche. Natürlich, wenn Sie auch geschützte doppelte Anführungszeichen - dann sind wir wieder da wo wir angefangen haben. 😉
InformationsquelleAutor der Antwort Mark Brackett
Ihre Verteidigung würde fehlschlagen, wenn:
(im letzteren Fall müsste es etwas sein, das weiter ausgebaut wurden erst, nachdem Sie getan haben, Ihre ersetzen)
InformationsquelleAutor der Antwort AJ.
Patrick, sind Sie mit dem hinzufügen von einfachen Anführungszeichen um ALLE Eingaben, auch die numerische Eingabe? Wenn Sie numerische Eingabe, aber nicht setzen das in Anführungszeichen, und dann haben Sie eine Aufnahme.
InformationsquelleAutor der Antwort Rob Kraft
Was hässliche code alle, die Bereinigung von Benutzereingaben wäre! Dann die klobigen StringBuilder-Objekt für die SQL-Anweisung. Die prepared statement Methode resultiert in einer viel saubereren code und die SQL-Injection Vorteile sind eine wirklich nette Zugabe.
Auch, warum das Rad neu erfinden?
InformationsquelleAutor der Antwort JeeBee
Eher als das ändern einer einzelnen zu zitieren (was aussieht wie) zwei einfache Anführungszeichen, warum nicht einfach ändern, um ein Apostroph, ein Anführungszeichen, oder entfernen Sie Sie vollständig?
Entweder Weg, es ist ein bisschen ein Durcheinander... vor allem, wenn Sie berechtigterweise Sachen (wie Namen), die Verwendung von single quotes...
HINWEIS: Ihre Methode übernimmt auch alle arbeiten auf Ihre app immer vergisst zu desinfizieren Eingabe, bevor Sie auf die Datenbank, das ist wahrscheinlich nicht realistisch, die meisten der Zeit.
InformationsquelleAutor der Antwort Kevin Fairchild
Es könnte funktionieren, aber es scheint ein wenig kitschig auf mich. Ich würde empfehlen, die überprüfung, dass jede Zeichenfolge gültig ist, indem Sie testen es mit einem regulären Ausdruck statt.
InformationsquelleAutor der Antwort Rob
Während Sie könnte eine Lösung finden, die Werke für Streicher, für die numerische Prädikate müssen Sie auch sicherstellen, dass Sie nur am Rande in zahlen (einfach zu überprüfen ist, kann es analysiert werden, wie int/double/decimal?).
Es ist eine Menge zusätzlicher Arbeit.
InformationsquelleAutor der Antwort Joseph Daigle
Ja, Sie können, wenn...
Nach dem Studium das Thema, ich denke, Eingang sanitized, wie Sie vorgeschlagen ist sicher, aber nur unter den folgenden Regeln:
Ihnen nie erlauben string-Werte kommen von Benutzern, die nichts weiter als string-Literale (d.h. vermeiden, dass die Konfiguration die option: "Geben Sie zusätzliche SQL-Spalte mit Namen/Ausdrücke hier:"). Wert andere Typen als Zeichenketten, zahlen, Datumsangaben, ...): konvertieren Sie Sie in Ihren systemeigenen Datentypen und geben Sie eine routine für SQL-literal von jedem Datentyp.
entweder man nutzt
nvarchar
/nchar
Spalten (und Präfix-string-Literale mitN
) ODER limit-Werte gehen invarchar
/char
Spalten ASCII-Zeichen (z.B. throw-exception beim erstellen von SQL-Anweisung)Sie immer überprüfen Wert Länge passen Spaltenlänge (Ausnahme auslösen, wenn mehr)
stellen Sie sicher, dass
SET QUOTED_IDENTIFIER
ist immerON
Beachtung dieser 4 Punkte, sollten Sie sicher sein. Wenn Sie gegen einen von Ihnen, einen Weg für SQL Injektion öffnet.
InformationsquelleAutor der Antwort miroxlav