2008-11-28 6 views
6

Ich arbeitete gerade an einer lokalisierbaren Lua-String-Lösung, als ich mit diesem Hack kam, Problem ist, ich weiß nicht, wie man davon gehackt wird zu vermeiden :) Also ich frage mich, ob jemand, etwas ähnliches getan hat und oder weiß, wie man vor dieser Art von Angriff schützt. (In Benutzercode)Gibt es in Lua trotzdem ein Sicherheitsproblem?

Da wir dies tun können:

=("foo"):upper() -->output: FOO 

Es kann wie folgt gehackt werden:

getmetatable("foo").__index.upper = function() print("bye bye sucker");os.exit() end 
=("foo"):upper() -->output: bye bye sucker (application quits) 
-- or this way 
=string.upper("bar") -->output: bye bye sucker (application quits) 

Irgendwelche Ideen?

+1

Keine Notwendigkeit, die Zeichenfolge metatable zu verwenden; es ist einfach die globale Tabellenfolge. Durch die Verwendung von string.upper = function ... können die Endbenutzer die Funktion weiterhin ändern. – jpjacobs

Antwort

8

In erster Linie führen Sie nicht vertrauenswürdigen Code nur in einer Sandbox-Umgebung aus - wie es von anderen Postern gesagt wurde. Abgesehen vom Laden von Bytecode-Chunks, erlaubt Lua alle anderen Sandboxing-Probleme abzudecken. (Und Bytecode-Chunk-Probleme werden sofort behoben, sobald sie entdeckt werden.)

Ein Beispiel für Sandboxing finden Sie unter Lua Live Demo.Quellen sind verfügbar here.

Ihr spezifisches Problem mit Metatables wird durch Setzen eines __metatable Feld gelöst:

Wenn Sie ein __metatable Feld in der Metatabelle gesetzt, getmetatable den Wert dieses Feldes zurückkehren, während setmetatable einen Fehler erhöhen .

- Roberto Ierusalimschy, Programmierung in Lua 1. Auflage, 13,3 - Library-Defined Metamethods

Zum Beispiel:

> mt = { __metatable = true }             
> t = {} 
> setmetatable(t, mt) 
> setmetatable(t, mt) 
stdin:1: cannot change a protected metatable 
stack traceback: 
[C]: in function 'setmetatable' 
stdin:1: in main chunk 
[C]: ? 

Also, alles, was Sie tun müssen, ist:

getmetatable("").__metatable = true 
+0

__metatable was ich gesucht habe, hatte das vergessen! –

6

Wenn Ihr Hacker die Fähigkeit hat, Code hinzuzufügen, und Sie müssen diesen Code erlauben, Dinge wie os.exit zu nennen, dann sind Sie ziemlich viel Glück sowieso.

Sie können jedoch die Funktionen einschränken, die ihr Code aufrufen kann. Das hängt davon ab, was der Benutzercode weiterhin tun soll. Siehe das Dokument für setfenv und google für "lua sandbox"

+0

Ich meine natürlich os Modul ist nicht verfügbar für Benutzer, aber ich habe es für den Impact-Faktor in meinem Code. Anyways danke für die Sandbox-Idee, hatte nicht daran gedacht, das zu googeln. –

2

Ich bin mir nicht sicher, warum Sie ein Problem haben, da Sie wahrscheinlich bereits wissen über Sandboxes: Sie können gefährliche Funktionen wie io.exit entfernen, und Sie können die überschriebenen sicherstellen Funktionen sind nur diejenigen in der globalen Tabelle des Benutzers, dh. Die von Ihrer Anwendung intern verwendeten Lua-Funktionen bleiben erhalten.
In jedem Fall, wenn der Hacker os.exit direkt aufrufen kann, ist die Tatsache, dass er sich selbst in den Fuß schießen kann, indem er eine unschuldige Funktion erschießt, die er später verwenden wird, sein Problem.
Außerdem ist es ein Problem nur wenn Sie Benutzerfunktionen auf Ihrem Server ausführen, zum Beispiel: wenn der Hacker sein System zerstört, ist das sein Problem!
Jetzt gibt es auch das Problem der Verbreitung von gefährlichem Code: Es liegt an Ihnen, die Leistungsfähigkeit von Benutzer-Skripten einzuschränken. Das machen Browser mit JavaScript.

+0

Das Problem ist das Überschreiben von string.upper, nicht direkt mit os.exit. Aber ich bin mir nicht sicher, ob Sandboxing direkt gegen das Überschreiben schützt, aber jetzt, wo Sie es erwähnen, sollte ich auch die get/setmetatable Funktionen aus der Benutzerumgebung verstecken. –

0

Ich habe keine Lösung (ich benutze nicht Lua, ich interessiere mich nur aus der Ferne), aber was Sie suchen, wird eine "Sandbox" genannt. Google für Lua sandbox, fand ich ein paar scheinbar interessante Seiten auf diese Weise. Zum Beispiel: http://lua-users.org/wiki/SandBoxes.

2

Dieses Sicherheitsproblem typischerweise mit diesem Satz illustriert sagte, von Ford Prefect in den brillanten Büchern Per Anhalter durch die Galaxis: It rather involved being on the other side of this airtight hatchway

Meine Fähigkeit, Code schreiben kann eine Sicherheit sein, nicht gesagt werden, Sicherheitslücke, und wenn Sie Ihren Code nicht kontrollieren können, , dass ist Ihr Sicherheitsproblem, nicht, was dieser Code tun kann.

Es gibt Unmengen von Dingen, die Sie tun können, wenn Sie nur die Maschine dazu bringen können, etwas von Ihrem Code auszuführen. Die Sicherheit besteht darin, zu vermeiden, dass der Code überhaupt dort ankommt. Alles danach ist nur Kollateralschaden.

Um dieses Problem zu vermeiden, sollten Sie vermeiden, unbekannten Code in Ihre Anwendung zu bekommen.

+0

+1 für die Realitätsprüfung, aber mein Ziel ist es, einige Benutzercode ausgeführt werden. Aber ja, du hast Recht, ich muss mein Problem hier überdenken –

+0

Die Sandbox-Ansatz, die andere erwähnen, ist mir unbekannt, so scheint es, dass Sie eine Möglichkeit haben, diese Fähigkeit in diesem Fall zu begrenzen. –

1

Ich sehe nicht die Möglichkeit, upper als das Problem zu definieren. In der Lage zu sehen os.exit ist das Problem.

Wie von anderen vorgeschlagen, erstellen Sie eine Sandbox-Umgebung für Ihre Skripts. Jedes Skript kann ein neues erhalten; dann kann eine Person das Obere oder etwas Ähnliches neu definieren, und alles, was sie vermasseln, ist ihr eigenes Ding.

Erstellen Lua-Status ist so schnell und einfach, das wird keine Probleme verursachen.

Eine weitere Sache, vor der Sie sich hüten könnten, sind die ewigen Schleifen. Wenn man einen "Watchdog" macht, der ein Skript nach etwa 10000 Anweisungen abtötet, benötigt man etwa 10 Zeilen C-Code. Ich kann Ihnen Probe schicken, wenn Sie brauchen.