简体   繁体   中英

Is mysql_real_escape_string() unsafe against hexadecimal encoded data?

We know that all user input must be escape by mysql_real_escape_string() function before executing on mysql in php script. And know that this function insert a \\ before any ' or " character in user input. suppose following code:

$_POST['username'] = 'aidan';
$_POST['password'] = "' OR ''='";

// Query database to check if there are any matching users
$query = "SELECT * FROM users WHERE user='".mysql_real_escape_string($_POST['username']."' AND password='".mysql_real_escape_string($_POST['password']."'";

mysql_query($query);

// This means the query sent to MySQL would be:
echo $query;

this code is safe.

But I find out if user enters her inputs with hexadecimal format then mysql_real_escape_string() can not do any thing and user can execute her sql injection easily. in bellow 27204f522027273d27 is same ' OR ''=' but in hex formated and sql execute without problem :

$_POST['username'] = 'aidan';
$_POST['password'] = "27204f522027273d27";

// Query database to check if there are any matching users
$query = "SELECT * FROM users WHERE user='".mysql_real_escape_string($_POST['username']."' AND password='".mysql_real_escape_string($_POST['password']."'";

mysql_query($query);

// This means the query sent to MySQL would be:
echo $query;

But whether this is true and if answer is yes how we can prevent sql injection in this way?

If you are using mysql_real_escape_string() , odds are you would be better served using a prepared statement.

For your specific case, try this code:

/*
Somewhere earlier in your application, you will have to set $dbh
 by connecting to your database using code like:
$dbh = new PDO('mysql:host=localhost;dbname=test', $DBuser, $DBpass);
*/

$_POST['username'] = 'aidan';
$_POST['password'] = "' OR ''='";

$user = $_POST['username'];
$password = $_POST['password'];

// Query database to check if there are any matching users
$query = "SELECT * FROM users WHERE user=? AND password=?";

$stmt = $dbh->prepare($query);
$stmt->bindParam(1, $user);
$stmt->bindParam(2, $password);
$stmt->execute();

This does require you to use PDO for your database interaction, but that's a good thing overall. Here's a question discussing the differences between PDO and mysqli statements .

Also see this StackOverflow question which is remarkably similar to yours and the accepted answer, from which I poached some of this answer.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM