понедельник, 13 мая 2013 г.

When Integer cannot protect you from SQL injection?

It is assumed that the cast user data to a numeric type is fully protected from SQL injection vulnerabilities.

Look at simple example:

$action = $_GET['do'];
$r=$db->query("select role".((int)$action)." from users where id=".((int)$_SESSION['user_id']));
if($row=$r->fetchArray()){
        if((int)$row[0]!==1){
                die('permission denied');
        }else{
                doAction($action);
        }
}


This code looks like SQLi protected, but it is not true.

Do not forget two obvious facts:
1. Minus is SQL operatator
2. Numbers can be negative

Now its easy to understand SQL logic in this case (w/o injection):

select role0 from users where id=0

And SQL injection attack vector in this case:

select role-1 from users where id=0


In our example attacker can bypass auth.
This example requires tables role and role0 both in database.