2014年11月

nginx下的php安全隔离

  • 方法1)在Nginx配置文件中加入

fastcgi_param PHP_VALUE "open_basedir=$document_root:/tmp/:/proc/:$document_root/../";

or

fastcgi_param PHP_ADMIN_VALUE "open_basedir=$document_root:/tmp/:/proc/:$document_root/../";

不同的地方是:php_admin_value(php_admin_flag)命令只能用在apache的httpd.conf文件中,而 php_value(php_flag)则是用在.htaccess文件中的,nginx下相同。

因为使用FastCGI,php不是每次都重新启动,所以每个主机sever都需要加入配置,以便每次访问都设置php的open_basedir。

适用 nginx + php5.3以上,php5.2 此方法不生效。

  • 方法2)在php.ini中加入:

open_basedir=./:/tmp/:/proc/
这种方式的设置需要重启php-fpm后生效

  • 方法3)在网站根目录下创建.user.ini并写入:

open_basedir=./:/tmp/:/proc/

这种方式不需要重启nginx或php-fpm服务。安全起见应当取消掉.user.ini文件的写权限。

关于.user.ini文件的详细说明:
http://php.net/manual/zh/configuration.file.per-user.php

  • 方法4)nginx的chroot

完全隔离php和系统,如果需要系统功能的自己创建系统环境,路径也要配成相对隔离的环境。
http://www.baidu.com/s?wd=nginx%20chroot

目前最好的是适用第一种方法。

设置open_basedir的同时最好禁止下执行命令的函数,比如:
shell_exec('ls /etc')仍然查看到/etc目录的文件列表
shell_exec('cat /etc/passwd')仍可查看到/etc/passwd文件的内容

建议禁止的函数如下:
disable_functions = pcntl_alarm, pcntl_fork, pcntl_waitpid, pcntl_wait, pcntl_wifexited, pcntl_wifstopped, pcntl_wifsignaled, pcntl_wexitstatus, pcntl_wtermsig, pcntl_wstopsig, pcntl_signal, pcntl_signal_dispatch, pcntl_get_last_error, pcntl_strerror, pcntl_sigprocmask, pcntl_sigwaitinfo, pcntl_sigtimedwait, pcntl_exec, pcntl_getpriority, pcntl_setpriority, eval, popen, passthru, exec, system, shell_exec, proc_open, proc_get_status, chroot, chgrp, chown, ini_alter, ini_restore, dl, pfsockopen, openlog, syslog, readlink, symlink, popepassthru, stream_socket_server, fsocket, chdir

php运行的几种运行方式

php本身是一个php代码的脚本执行程序,运行方式是指其运行的方法。整理归纳为一下五种方法:

  • 模块加载运行方式 (Apache)
  • CGI运行方式 (Apache)
  • FastCGI运行方式 (几乎通用Apache nginx lighttp)
  • ISAPI运行方式 (window下Apache)
  • cli运行方式 (就是命令行)

前四种是提供给web服务器来处理php代码文件,其中模块加载的方式其实是最快的的,但FastCGI配合nginx WEB服务是目前的主流,下面主要配合Apache做说明。

- 阅读剩余部分 -