PHP sprintf считается вредным? - PullRequest
3 голосов
/ 27 марта 2012

Несколько лет назад я узнал о Форматировании строковых атак в Си сложным путем.Теперь я недавно увидел некоторый код PHP, подобный этому:

<?php
echo sprintf($_GET['format'], $_GET['value1'], $_GET['value2']);

Я пытался запустить это так с $_GET['format'], для которого установлены строки типа %s%s%s..., но PHP просто существует с PHP Warning: sprintf(): Too few arguments in file.php on line 2.Разве все еще не возможно провести атаку форматной строки?

Ответы [ 4 ]

3 голосов
/ 27 марта 2012

Не в традиционном смысле, поскольку PHP sprintf не поддерживает ни одно из действительно опасных преобразований, таких как %n.Контролируемая пользователем строка формата все еще может вызывать некоторые ограниченные разрушения (рассмотрим %99999999s), но самое худшее, что я думаю, это может потребовать использование памяти и времени.

2 голосов
/ 28 марта 2012

Я также обнаружил целочисленное переполнение. Что приводит к этому:

<?php
echo sprintf('%2147483646$s', "foo"); # Warning: Too few arguments
echo sprintf('%2147483647$s', "foo"); # Warning: Argument number must be greater than zero

Я подал это как Ошибка PHP # 61531 . Я не уверен, что это может быть использовано.

0 голосов
/ 27 марта 2012

Не уверен, что существует уязвимость PHP sprintf (), но пример кода, как представляется, является ярким примером того, как не нужно ничего делать.

Насколько мне известно, sprintf должен помочь вам заблокировать строку, а не наоборот. Например, это то, что я считаю полезной причиной для использования sprintf ():

$sql = sprintf(
    "insert into table (myname, myvalue) values ('%s', '%s')",
    mysql_real_escape_string( $_GET['name'] ),
    intval( $_GET['value'] )
);

Более полезная причина использовать sprintf - позаимствовать его двоюродного брата, vsprintf и постоянно использовать:

// takes variable number of parameters
function sanitize() {
    $args = func_get_args();
    $sql = array_shift( $args );
    foreach( $args as $k => $v ) $args[$k] = mysql_escape_string( $v );
    $safe_sql = vsprintf( $sql, $args );
    return( $safe_sql );
}

С его помощью вы можете безопасно изолировать параметры от запросов и предположить, что они будут обработаны:

$t = mysql_query(sanitize(
    "insert into mytable (myname, myvalue) values ('%s', '%s')",
    $_GET['name'],
    $_GET['value']
));
0 голосов
/ 27 марта 2012

Языки более высокого уровня, как правило, проверяют количество передаваемых аргументов, а не слепо доверяют программисту.Вам нужно будет найти другой вектор атаки.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...