PHP, the scripting language of choice for a lot of dynamic content unfortunately contains some pretty useless and downright stupid features. This article explains what they are, why you shouldn't use them and how to disable them. The article may also be somewhat biased as I'm honestly not a fan of how easily PHP enables newbie coders to whip up scripts full of coding errors and security holes.
register_globals
I'm not sure who came up with the idea that remote users should be able to taint the namespace of executing scripts, but it certainly wasn't a very smart idea. register_globals is a feature that turns your PHP scripts into a security nightmare. In a nutshell, it automatically creates global variables based on user input. Say you have a script foo.php and someone accesses http://www.example.com/foo.php?hack=1 PHP will then create a variable $hack and assign the value "1" to it without you even doing anything in the code to request such. While this sounds innocent enough, many poorly coded PHP scripts do not correctly initialize variables and use code such as this:
if ($_COOKIE['adminpassword'] == 'secret')
$admin = TRUE;
...
if ($admin)
destroy_website();
At first glance it would seem that $admin is only set to TRUE if the password matches. With register_globals enabled however, an attacker simply has to pass a paramater called admin with the value 1 and they will have admin privileges also. This is easily done by accessing the script like http://www.example.com/insecure.php?admin=1
It is interesting to check the security history of even supposedly well-designed PHP scripts such as commercial forum software. Almost always you can find an instance where register_globals is responsible for some problem. Becuase PHP executes the register_globals function and pollutes your namespace before your script even begins execution, there is no way to disable this feature from within a PHP script. Fortunately it can be disabled through the use of a .htaccess file with the following line:
#Disable insecure and dangerous register_globals
php_flag register_globals 0
Although register_globals now defaults to off in the PHP distribution, the majority of web hosting providers re-enable it to maintain compatibility with old and buggy PHP scripts. Thus you should always take steps to explicitly disable it whenever you are distributing or using a PHP script.
Magic Quotes
In 2nd place to register_globals, we have 'magic quotes'. Or given a better name, 'random escaping'. This feature randomly sticks a \ (backslash) in front of certain characters in user-supplied input. This is supposed to make the user input safe to use in a database query for example. Except that it isn't safe, since each database has its own escaping requirements and thus its own functions such as mysql_real_escape_string. Instead, what you get is mangled user input that you have to run stripslashes on before you can even do anything with it.
Say for example you are asking the user to input a password in a simple HTML form field called 'password'. The users' password is Can'tHackThis. When your HTML form is POSTed to your PHP script, you would imagine the $_POST['password'] variable to contain Can'tHackThis. Instead, it contains Can\'tHackThis because magic quotes was enabled and mangled the user input for you.
I could understand the use of such a function if for example you could specify that 'All user input that comes to this PHP script is going to be passed to a MySQL database so escape it using mysql_escape_string'. But most of the time your user input isn't going to go straight into an SQL statement, leaving you with input full of escape characters that you don't want.
What bugs me the most though is the whole nature of the magic quotes (and addslashes/stripslashes -- see below). They are not escaping the data to any kind of standard - you can't use it in an SQL statement since it doesn't have database-specific characters escaped! I've yet to see a single legitimate use of magic quotes that hasn't been a coding error.
PHP scripts that aren't expecting magic_quotes to be enabled often suffer when it is suddenly placed upon them by the server settings. A common manifestation is to see web pages full of randomly escaped characters such as strings of \' and \\.
Like register_globals, this cannot be disabled from within a PHP script - you require a .htaccess option:
These two functions tie in very closely with magic quotes. Magic quotes simply applies addslashes to user input and stripslashes removes those slashes. Again, my gripe with these functions is that there is no point! The strings that you get as a result of addslashes are still unsafe for use in any SQL query because they haven't been escaped with a database-specific escape function such as mysql_real_escape_string.
As with magic quotes, any use of these two functions is often a coding error. The one exception is if for some reason you cannot disable magic quotes using .htaccess as above, in which case you could use stripslashes on all the user input to de-mangle the user input.
Example .htaccess file
Here is a sample .htaccess file you may wish to use to disable these features.