Neuigkeiten:

Privates MODX und LINUX BLOG, User Registrierung ist deaktiviert! Fragen oder Tipps? Bitte per Matrix: @jolichter:tchncs.de

Hauptmenü

Thema 777er-Rechte bei Dateien

Begonnen von Wasi, 2006-04-27 | 12:49:05

« vorheriges - nächstes »

Wasi

Mal was zum Nachdenken und zum Thema chmod 777er-Rechte bei Dateien

Wenn (wie bei vielen) PHP als Modul läuft, dann bedeuted das, das der PHP-Interpreter unter den globalen Rechten des Web-Servers ausgeführt wird. Also oft als User "wwwrun", "www-data" usw. PHP läuft also NICHT unter einer Kundenspezifischen gid/uid-Umgebung.
Die Webs der User auf einem Webserver müssen(!) für diesen globalen User freigegeben sein, weil ansonsten ja gar kein PHP ausgeführt werden könnte.
Soweit so gut ...
Üblicherweise "schützt" man den Kunden/webübergreifenden Zugriff (ausspionieren) durch das Setzen der base_dir-Restriktion. Sobald PHP also auf ein fremdes Web zugreifen will, wird es daran gehindert.

Fatal wird es nun, wenn der safemode=off steht (wie überall gefordert) und exec() erlaubt sein soll (auch vielfach gefordert, weil man ja ImageMagick braucht usw.). In dieser Kombination greift der safemode_exec_path nicht mehr und alle Webs liegen schlagartig offen, denn durch exec() aufgerufene Programme auf dem Server kümmern sich nicht um das oben_basedir für PHP (kennen sie ja gar nicht, weil es keine PHP-Scripte sind). Diese Programme laufen unter der uid/gid des aufgrufenden Prozesses, also des Webservers (wwwrun usw.). Und wie oben festgestellt wurde, hat dieser User quasi überall in anderen Webs Zugriff. Den Rest überlasse ich der Phantasie... Mit "Hacken" hat eigentlich nichts mehr zu tun, wenn ein User derart simpel die Daten fremder Webs auslesen kann...

Um wenigstens eine Basis-Sicherheit zu schaffen, sind daher bestimmten Kombinationen unbedingt zu vermeiden. Am schlimmsten ist:

safemode=off
in Verbindung mit
exec() erlaubt

Wenn exec() erlaubt sein soll, dann nur:
-mit safemode=on
-und safemode_exec_dir gesetzt

Systembedingt am sichersten ist es, wenn PHP unter einer einmaligen(!) uid/gid des jeweiligen Webs läuft. Dazu wird eine Wrappertechnik eingesetzt (suPHP, suexec, fastcgi etc.). Im übrigen ist hier dann auch das gesamte "wwwrun-Problem" gelöst, weil es erst gar nicht auftritt, weil FTP-User, Web-User und PHP-User alle genau denselben Systemuser benutzen, welcher nur im eigenen Web sinnvollen Zugriff hat - sofern keine 777er-Rechte gesetzt werden - wobei ich wieder beim Anfang des Posting bin.

Was ich letztlich sagen will:
Auf vielen Servern haben die User gar keine Möglichkeit sich zu schützen, weil das System sperrangelweit offensteht. Auf diesen Servern darf man auch ruhig 777 setzen, denn 644 wäre auch nicht sicherer.

:p

Jo

#1
Du kannst den Apache-Webserver der Version 2 mit den Rechten eines individuellen Systemusers ausführen lassen. Das läßt sich je VHOST individuell einstellen. Um PHP oder auch Perl-Scripte dazu zu bewegen, werden Wrappertechniken angewendet: suexec, fastCGI, suPHP. Es gibt noch andere.
Sinnvollerweise ordnet man je VHOST einen eigenen Systemuser zu. Mit diesem User wird auch der jeweilige FTP-Zugang eingerichtet. Dann hast Du ein Web, das nur einem einizgen User "gehört" und Du kannst das Datei-Rechtesystem voll zur Geltung bringen.

Das sind letztlich keine Geheimnisse. PHP wird "als CGI" installiert, wie man so schön sagt. Das hat aber nichts mit dem "cgi-bin"-Verzeichnis zu tun. Man findet diverse Installationsanleitungen für die jeweiligen Linux-Distributionen. Hier z.B. eine für Debian.
Im Endeffekt sind dann alle Prozesse um Web, FTP und PHP eindeutigen Usern zugeordnet. Damit lassen sich Prozesse besser überwachen, zuordnen und auch limitieren. Eigene Limits und Konfigurationen je Web sind kein Problem und querlaufende Prozesse (Spams mit Scripten, Spionagescripte etc.) lassen sich zuordnen usw.

Wo Licht ist, ist auch Schatten: Die Installation einer solchen Umgebung ist deutlich komplexer. Wird die übliche Verwaltungssoftware wie Confixx, Plesk, VHCS etc, eingesetzt, muss man PHP auch als übliches Apache-Modul einrichten.

Ein gängiges Vorurteil ist, das PHP dann langsamer wäre. Das ist völliger Unsinn, denn es werden dieselben Binaries aufgerufen, nur der Kontext zum Aufruf ist anders.
Richtig ist, das ein Scriptaufruf mehr Rescourcen benötigt und daher ein Server stärker beansprucht wird, als bei mod_PHP. Solange ein Server aber im "grünen Bereich" arbeitet, gibt es keine Performanceunterschiede.
In der Praxis wird "PHP als CGI" nur vereinzelt angewendet. Ohne jetzt einzelnen Hostern zu nahe treten zu wollen, aber der Grund ist einfach: Leichter zu installieren und man bekommt mehr Kunden auf den Server. Im Zeitalter des Hosting-Dumpings scheinbar eine notwendige Maßnahme...
Es gibt aber noch genug andere, beispielsweise "schwarzkünstler" - auch ein Hoster mit diesem Konzept. Vereinzelt findet man solche Pakete auch bei anderen. Dennoch muss man aufpassen. "PHP als CGI" alleine ist keine Garantie. Das Gesamtkonzept muss schon stimmen.


Wasi

#2
Hallo Jo,
da auch Du mit PHP arbeitest hier noch ein Tipp:

Auf vielen Webseiten klafft noch immer eine große Sicherheitslücke.
Alte PHP-Versionen übernehmen ohne Prüfung Variablen, die ihnen per POST oder aus der URL übergeben werden.

Sprich, eine URL wie

www.google.de/seite.php?var=1

setzt im PHP-Skript die Variable $var auf den Wert 1. Das mag bequem sein. Aber wer böses will, kann beliebige andere Variablennamen an eine URL anhängen und diese so ins Programm einschmuggeln. Und wer hat nicht zum Beispiel einen Schleifenzähler namens $i oder die Kennwort-Variable $password?

Um diese Sicherheitslücke zu schließen, gibt es seit PHP-Versionen 4.1 in der php.ini den Parameter register globals. Ist der auf off gesetzt, funktioniert das Schmuggeln nicht mehr. Um Ihren Programmcode auf das Sicherheitsplus anzupassen, verwendet $_GET und $_POST. Damit könnt Ihr per URL oder Formular Variablen übergebenen, etwa:

$strUsername = $_GET['user'];

Diese Anweisung holt aus einer URL wie

www.google.de/seite.php?user=max

den Benutzernamen "max" und weist ihn der Variable $strUsername zu. Auf diese Weise funktioniert der Code auch, wenn register_globals auf off gestellt ist. Sobald Ihr die Änderungen vorgenommen haben, bittet Ihr Euren Provider, den Parameter auf off zu stellen. Mehr Info dazu:

http://www.php.net/register_globals