note 83811 added to security.variables
| From: | Viz at osu1 dot php dot net | Date: | Thu, 12 Jun 2008 17:47:08 +0000 |
| Subject: | note 83811 added to security.variables | ||
| Groups: | php.notes | ||
| Request: | Send a blank email to php-notes+get-140388@lists.php.net to get a copy of this message | ||
@f dot zijlstra
Actually you should not filter against known bad data, you need to white list your filters. Rather
than looking for bad data, you should strip everything but what you expect because it's future
proof.
example for a 32 character text input field:
$inputvar=substr(htmlentities($_POST['inputvar']),0,32);
$inputvar=preg_replace('/[^\w\.\-\& ]/', '', $inputvar);
This will strip numbers, newlines, null characters, # and all non-printable characters, only
allowing word characters(determined by locale setting), .,-, space and &, as well as truncate
the value to the size you accept. You could use preg_match instead and throw an error if
there's anything outside the pattern.
This can be a little painful because you might miss a character you need, and have to add it to your
code, but it's easier than restoring your database, or explaining to your customers about why
their data is now in the hands of identity thieves.
Default deny for the long term win. It's the only security panacea that works now and always
will. Blacklists are the completely wrong approach because they don't handle future threats you
don't know about yet.
Further you should use mysqli and prepared statements for queries which use user data as parameters,
after using the mysql filters on the input data. If you really want to go the extra mile, start
using stored procedures because it will allow you to remove SELECT, DELETE, UPDATE and INSERT
permissions from the web server user. All you need is EXECUTE for stored procs, thereby limiting
what can be seen of the database to only the functions you expose(and you can easily expose too much
if you aren't careful).
Naturally the big dangers are SQL injection and XSS. A simple filter like this will break them when
combined with a prepared statement.
As someone else noted, relying on _anything_ from the client is an extremely bad idea because it can
all be spoofed (including HTTP_REFERER) using Paros, Tamper Data or any other client side proxy, by
doing a simple man in the middle tamper on yourself.
You can make HTTP_REFERER=http://www.whitehouse.gov if you
want.
Sorry to segway into db security, but you can't avoid it when talking about sanitizing input
which leads to building queries.
-Viz
----
Server IP: 208.69.120.35
Probable Submitter: 66.240.11.2
----
Manual Page -- http://www.php.net/manual/en/security.variables.php
Edit -- https://master.php.net/note/edit/83811
Del: integrated -- https://master.php.net/note/delete/83811/integrated
Del: useless -- https://master.php.net/note/delete/83811/useless
Del: bad code -- https://master.php.net/note/delete/83811/bad+code
Del: spam -- https://master.php.net/note/delete/83811/spam
Del: non-english -- https://master.php.net/note/delete/83811/non-english
Del: in docs -- https://master.php.net/note/delete/83811/in+docs
Del: other reasons-- https://master.php.net/note/delete/83811
Reject -- https://master.php.net/note/reject/83811
Search -- https://master.php.net/manage/user-notes.php