Что это за строка?

Строка ))) AND EXTRACTVALUE(9028,CONCAT(0x7e,((SELECT (ELT(9028=9028,1)))),0x7e))-- - представляет собой фрагмент вредоносного SQL-кода, который злоумышленник пытается внедрить в уязвимый параметр веб-приложения. Это классический пример error-based SQL-инъекции (инъекции, основанной на ошибках) для СУБД MySQL. Подобные конструкции встречаются в логах веб-серверов, в полях ввода форм или в параметрах URL, когда автоматизированный сканер или хакер проверяет сайт на наличие уязвимостей.

Основная цель такой инъекции — заставить базу данных выдать сообщение об ошибке, которое содержит интересующие злоумышленника данные (например, имя базы, версию СУБД, логины и пароли пользователей). Функция EXTRACTVALUE() здесь используется как инструмент для генерации ошибки, в текст которой подставляется результат выполнения вложенного запроса.

Разбор по частям: что делает каждая функция

Чтобы понять смысл всей строки, разберём её компоненты.

EXTRACTVALUE()

Функция EXTRACTVALUE() в MySQL принимает два строковых аргумента: фрагмент XML-разметки и выражение XPath. Она возвращает текст (CDATA) первого текстового узла, который является дочерним для элемента или элементов, соответствующих XPath-выражению. Если XPath-выражение синтаксически некорректно, функция генерирует ошибку XPATH syntax error. Именно на этой особенности и строится эксплойт: злоумышленник передаёт в качестве XPath строку, содержащую результат подзапроса, и эта строка попадает в сообщение об ошибке, которое затем отображается на странице.

CONCAT() и 0x7e

CONCAT() объединяет строки. Шестнадцатеричное значение 0x7e соответствует символу тильды ~. Тильда используется как маркер-разделитель, чтобы в выводе ошибки было легко найти начало и конец внедрённых данных. Конструкция CONCAT(0x7e, ((SELECT ...)), 0x7e) создаёт строку вида ~результат~, которая затем передаётся в EXTRACTVALUE() как XPath-выражение. Поскольку тильда не является допустимым символом XPath, MySQL выдаёт ошибку, содержащую эту строку.

SELECT (ELT(9028=9028,1))

Вложенный подзапрос SELECT (ELT(9028=9028,1)) возвращает число 1. Функция ELT() возвращает N-й элемент из списка: ELT(N, строка1, строка2, ...). В данном случае N — это результат сравнения 9028=9028, который всегда истинен и равен 1. Соответственно, ELT(1, 1) вернёт первый элемент списка — 1. Это простейший пример, демонстрирующий работу инъекции. В реальной атаке вместо 1 мог бы стоять, например, database(), user() или version(), и тогда в ошибке отобразилось бы имя текущей базы, пользователь или версия MySQL.

Скобки и комментарий

Три закрывающие скобки ))) в начале нужны, чтобы «закрыть» ранее открытые скобки в оригинальном SQL-запросе уязвимого приложения. Это позволяет внедрить конструкцию AND EXTRACTVALUE(...) без нарушения синтаксиса. Завершающая последовательность -- - — это комментарий в MySQL (пробел после двух дефисов обязателен, чтобы СУБД распознала комментарий). Всё, что идёт после -- -, игнорируется, что позволяет отбросить остаток оригинального запроса.

Как работает error-based SQL-инъекция

Механизм следующий:

  1. Приложение формирует SQL-запрос, подставляя в него пользовательский ввод без должной очистки.
  2. Злоумышленник передаёт в уязвимый параметр строку, подобную рассматриваемой.
  3. База данных выполняет запрос, и функция EXTRACTVALUE() получает на вход XPath-выражение, содержащее результат подзапроса (например, имя базы данных).
  4. Поскольку это выражение синтаксически неверно, MySQL генерирует ошибку вида XPATH syntax error: '~имя_базы~'.
  5. Если приложение выводит сообщения об ошибках БД на страницу (что часто бывает в режиме отладки), злоумышленник видит эти данные.

Таким образом, даже без возможности прямого вывода данных атакующий может извлекать информацию посимвольно или целыми строками, используя ошибки как канал утечки.

Опасность и последствия

Error-based SQL-инъекции считаются одними из самых опасных, потому что позволяют получить доступ к содержимому базы данных. В руках злоумышленника это может привести к:

  • утечке конфиденциальных данных (пароли, персональные данные, платёжная информация);
  • обходу аутентификации и получению прав администратора;
  • изменению или удалению данных;
  • полному захвату сервера в случае наличия дополнительных уязвимостей.

Подобные строки часто встречаются в логах, когда сайт сканируют автоматические инструменты (например, sqlmap). Это может быть как попытка реальной атаки, так и просто шум от ботов.

Как защититься

Основной способ защиты — использовать параметризованные запросы (prepared statements) и хранимые процедуры, которые не позволяют пользовательскому вводу влиять на структуру SQL. Также важно:

  • отключить вывод подробных сообщений об ошибках БД на боевом сервере;
  • проводить валидацию и фильтрацию всех входных данных;
  • применять принцип наименьших привилегий для учётной записи, от имени которой работает приложение;
  • регулярно обновлять СУБД и использовать WAF (веб-application firewall).
Если вы обнаружили такую строку в логах, это сигнал о том, что ваш сайт пытались протестировать на уязвимость. Рекомендуется провести аудит безопасности и убедиться, что все запросы к базе данных параметризованы.

Заключение

Строка ))) AND EXTRACTVALUE(9028,CONCAT(0x7e,((SELECT (ELT(9028=9028,1)))),0x7e))-- - — это не случайный набор символов, а целенаправленный эксплойт для извлечения данных из MySQL через сообщения об ошибках. Понимание принципов его работы помогает разработчикам и администраторам лучше защищать свои приложения. Если вы встретили подобное в логах, отнеситесь к этому серьёзно: проверьте код на наличие SQL-инъекций и устраните уязвимости.

Источники