From a15d816e01041b4130b31b89eb675589d32d3ea9 Mon Sep 17 00:00:00 2001 From: Ron Chmara Date: Fri, 3 Aug 2001 07:13:02 +0000 Subject: [PATCH] Typos, improved code, page on obscuring PHP, rewording, changing examples for register_globals= off. git-svn-id: https://svn.php.net/repository/phpdoc/en/trunk@53118 c90b9560-bf6c-de11-be94-00142212c4b1 --- chapters/security.xml | 86 +++++++++++++++++++++++++++++++++++-------- security/index.xml | 86 +++++++++++++++++++++++++++++++++++-------- 2 files changed, 140 insertions(+), 32 deletions(-) diff --git a/chapters/security.xml b/chapters/security.xml index 3fc81e561c..1bd38ba4a6 100644 --- a/chapters/security.xml +++ b/chapters/security.xml @@ -1,4 +1,4 @@ - + Security @@ -330,7 +330,7 @@ AddHandler php-script .php <?php // remove a file from the user's home directory -$username = $user_submitted_name; +$username = $HTTP_POST_VARS['user_submitted_name']; $homedir = "/home/$username"; $file_to_delete = "$userfile"; unlink ($homedir/$userfile); @@ -378,7 +378,7 @@ echo "/home/../etc/passwd has been deleted!"; <?php // removes a file from the hard drive that // the PHP user has access to. -$username = $HTTP_REMOTE_USER; // using an authentication mechanisim +$username = $HTTP_SERVER_VARS['REMOTE_USER']; // using an authentication mechanisim $homedir = "/home/$username"; @@ -386,7 +386,7 @@ $file_to_delete = basename("$userfile"); // strip paths unlink ($homedir/$file_to_delete); $fp = fopen("/home/logging/filedelete.log","+a"); //log the deletion -$logstring = "$HTTP_REMOTE_USER $homedir $file_to_delete"; +$logstring = "$username $homedir $file_to_delete"; fputs ($fp, $logstring); fclose($fp); @@ -402,7 +402,7 @@ echo "$file_to_delete has been deleted!"; More secure file name checking <?php -$username = $HTTP_REMOTE_USER; // using an authentication mechanisim +$username = $HTTP_SERVER_VARS['REMOTE_USER']; // using an authentication mechanisim $homedir = "/home/$username"; if (!ereg('^[^./][^/]*$', $userfile)) @@ -515,7 +515,7 @@ if (!ereg('^[^./][^/]*$', $username)) One way of catching this issue ahead of time is to make use of - PHP's own error_reporting(), to help you + PHP's own error_reporting, to help you secure your code and find variable usage that may be dangerous. By testing your code, prior to deployment, with E_ALL, you can quickly find areas where your variables may be open to poisoning @@ -543,8 +543,11 @@ if ($good_login == 1) { // If above test fails, not initialized or checked befor One feature of PHP that can be used to enhance security is configuring PHP with register_globals = off. By turning off the ability for any user-submitted variable to be injected - into PHP code, you can restrict the amount of variable - poisoning a potential attacker may inflict. + into PHP code, you can reduce the amount of variable + poisoning a potential attacker may inflict. They will have + to take the additional time to forge submissions, and your + internal variables are effectively isolated from user + submitted data. While it does slightly increase the amount of effort required @@ -568,8 +571,9 @@ if ($good_login == 1) { // can be forged by a user in get/post/cookies, Working with register_globals = off <?php -if($HTTP_COOKIE_VARS["username"]){ // can only come from a cookie - $good_login = 1; // cannot be forged by a user +if($HTTP_COOKIE_VARS['username']){ + // can only come from a cookie, forged or otherwise + $good_login = 1; fpassthru ("/highly/sensitive/data/index.html"); } ?> @@ -578,24 +582,31 @@ if($HTTP_COOKIE_VARS["username"]){ // can only come from a cookie By using this wisely, it's even possible to take preventative measures to warn when forging is being attempted. If you know ahead of time exactly where a variable should be coming from, - you can check to see if submitted data is inappropriate. + you can check to see if submitted data is coming from an + inappropriate kind of submission. While it doesn't guarantee + that data has not been forged, it does require an attacker + to guess the right kind of forging. - Detecting variable poisoning + Detecting simple variable poisoning <?php -if ($HTTP_COOKIE_VARS["username"] && - !$HTTP_POST_VARS["username"] && - !$HTTP_GET_VARS["username"] ) { +if ($HTTP_COOKIE_VARS['username'] && + !$HTTP_POST_VARS['username'] && + !$HTTP_GET_VARS['username'] ) { + // Perform other checks to validate the user name... $good_login = 1; fpassthru ("/highly/sensitive/data/index.html"); } else { - mail("admin@example.com", "Possible breakin attempt", "$REMOTE_IP_ADDR"); + mail("admin@example.com", "Possible breakin attempt", $HTTP_SERVER_VARS['REMOTE_ADDR']); echo "Security violation, admin has been alerted."; exit; } ?> + Of course, simply turning on register globals does not mean code + is secure. For every piece of data that is submitted, it + should also be checked in other ways. @@ -674,6 +685,49 @@ exec ($evil_var); + + Hiding PHP + + A few simple techniques can help to hide PHP, possibly slowing + down an attacker who is attempting to disover weaknesses in your + system. By setting expose_php = off in your php.ini file, you + reduce the amount of information available to them. + + + Another tactic is to configure web servers such as apache to + parse different filetypes through PHP, either with an .htaccess + directive, or in the apache configuration file itself. You can + then use misleading file extensions: + + Hiding PHP as another language + +# Make PHP code look like other code types +AddType application/x-httpd-php .asp .py .pl + + + Or obscure it completely: + + Using unknown types for PHP extensions + +# Make PHP code look like unknown types +AddType application/x-httpd-php .bop .foo .133t + + + Or hide it as html code, which has a slight performance hit because + all html will be parsed through the PHP engine: + + Using html types for PHP extensions + +# Make all PHP code look like html +AddType application/x-httpd-php .htm .html + + + For this to work effectively, you must rename your PHP files with + the above extensions. While it is a form of security through + obscurity, it's a minor preventative measure with few drawbacks. + + + General considerations diff --git a/security/index.xml b/security/index.xml index 3fc81e561c..1bd38ba4a6 100644 --- a/security/index.xml +++ b/security/index.xml @@ -1,4 +1,4 @@ - + Security @@ -330,7 +330,7 @@ AddHandler php-script .php <?php // remove a file from the user's home directory -$username = $user_submitted_name; +$username = $HTTP_POST_VARS['user_submitted_name']; $homedir = "/home/$username"; $file_to_delete = "$userfile"; unlink ($homedir/$userfile); @@ -378,7 +378,7 @@ echo "/home/../etc/passwd has been deleted!"; <?php // removes a file from the hard drive that // the PHP user has access to. -$username = $HTTP_REMOTE_USER; // using an authentication mechanisim +$username = $HTTP_SERVER_VARS['REMOTE_USER']; // using an authentication mechanisim $homedir = "/home/$username"; @@ -386,7 +386,7 @@ $file_to_delete = basename("$userfile"); // strip paths unlink ($homedir/$file_to_delete); $fp = fopen("/home/logging/filedelete.log","+a"); //log the deletion -$logstring = "$HTTP_REMOTE_USER $homedir $file_to_delete"; +$logstring = "$username $homedir $file_to_delete"; fputs ($fp, $logstring); fclose($fp); @@ -402,7 +402,7 @@ echo "$file_to_delete has been deleted!"; More secure file name checking <?php -$username = $HTTP_REMOTE_USER; // using an authentication mechanisim +$username = $HTTP_SERVER_VARS['REMOTE_USER']; // using an authentication mechanisim $homedir = "/home/$username"; if (!ereg('^[^./][^/]*$', $userfile)) @@ -515,7 +515,7 @@ if (!ereg('^[^./][^/]*$', $username)) One way of catching this issue ahead of time is to make use of - PHP's own error_reporting(), to help you + PHP's own error_reporting, to help you secure your code and find variable usage that may be dangerous. By testing your code, prior to deployment, with E_ALL, you can quickly find areas where your variables may be open to poisoning @@ -543,8 +543,11 @@ if ($good_login == 1) { // If above test fails, not initialized or checked befor One feature of PHP that can be used to enhance security is configuring PHP with register_globals = off. By turning off the ability for any user-submitted variable to be injected - into PHP code, you can restrict the amount of variable - poisoning a potential attacker may inflict. + into PHP code, you can reduce the amount of variable + poisoning a potential attacker may inflict. They will have + to take the additional time to forge submissions, and your + internal variables are effectively isolated from user + submitted data. While it does slightly increase the amount of effort required @@ -568,8 +571,9 @@ if ($good_login == 1) { // can be forged by a user in get/post/cookies, Working with register_globals = off <?php -if($HTTP_COOKIE_VARS["username"]){ // can only come from a cookie - $good_login = 1; // cannot be forged by a user +if($HTTP_COOKIE_VARS['username']){ + // can only come from a cookie, forged or otherwise + $good_login = 1; fpassthru ("/highly/sensitive/data/index.html"); } ?> @@ -578,24 +582,31 @@ if($HTTP_COOKIE_VARS["username"]){ // can only come from a cookie By using this wisely, it's even possible to take preventative measures to warn when forging is being attempted. If you know ahead of time exactly where a variable should be coming from, - you can check to see if submitted data is inappropriate. + you can check to see if submitted data is coming from an + inappropriate kind of submission. While it doesn't guarantee + that data has not been forged, it does require an attacker + to guess the right kind of forging. - Detecting variable poisoning + Detecting simple variable poisoning <?php -if ($HTTP_COOKIE_VARS["username"] && - !$HTTP_POST_VARS["username"] && - !$HTTP_GET_VARS["username"] ) { +if ($HTTP_COOKIE_VARS['username'] && + !$HTTP_POST_VARS['username'] && + !$HTTP_GET_VARS['username'] ) { + // Perform other checks to validate the user name... $good_login = 1; fpassthru ("/highly/sensitive/data/index.html"); } else { - mail("admin@example.com", "Possible breakin attempt", "$REMOTE_IP_ADDR"); + mail("admin@example.com", "Possible breakin attempt", $HTTP_SERVER_VARS['REMOTE_ADDR']); echo "Security violation, admin has been alerted."; exit; } ?> + Of course, simply turning on register globals does not mean code + is secure. For every piece of data that is submitted, it + should also be checked in other ways. @@ -674,6 +685,49 @@ exec ($evil_var); + + Hiding PHP + + A few simple techniques can help to hide PHP, possibly slowing + down an attacker who is attempting to disover weaknesses in your + system. By setting expose_php = off in your php.ini file, you + reduce the amount of information available to them. + + + Another tactic is to configure web servers such as apache to + parse different filetypes through PHP, either with an .htaccess + directive, or in the apache configuration file itself. You can + then use misleading file extensions: + + Hiding PHP as another language + +# Make PHP code look like other code types +AddType application/x-httpd-php .asp .py .pl + + + Or obscure it completely: + + Using unknown types for PHP extensions + +# Make PHP code look like unknown types +AddType application/x-httpd-php .bop .foo .133t + + + Or hide it as html code, which has a slight performance hit because + all html will be parsed through the PHP engine: + + Using html types for PHP extensions + +# Make all PHP code look like html +AddType application/x-httpd-php .htm .html + + + For this to work effectively, you must rename your PHP files with + the above extensions. While it is a form of security through + obscurity, it's a minor preventative measure with few drawbacks. + + + General considerations