Что такое EXTRACTVALUE и почему она в запросе?
Строка %"))) AND EXTRACTVALUE(6676,CONCAT(0x7e,((SELECT (ELT(6676=6676,1)))),0x7e))-- - — это не случайный набор символов, а классический пример error-based SQL-инъекции для СУБД MySQL. Такие конструкции используют для извлечения данных из базы данных через вывод сообщения об ошибке. В данном случае злоумышленник пытается заставить сервер выполнить функцию EXTRACTVALUE, которая при некорректных аргументах возвращает сообщение об ошибке, содержащее результат подзапроса.
Функция EXTRACTVALUE изначально предназначена для работы с XML: она принимает XML-документ и выражение XPath, возвращая значение найденного узла. Однако в руках атакующего она превращается в инструмент для извлечения произвольных данных, если приложение уязвимо к SQL-инъекциям.
Как работает error-based SQL-инъекция через EXTRACTVALUE
Механизм основан на том, что СУБД MySQL при определённых условиях выводит в сообщении об ошибке результат выполнения вложенного запроса. Рассмотрим по частям:
%")))— это часть исходного запроса, которая «ломает» его синтаксис, закрывая кавычки и скобки. Символ%часто используется в LIKE-запросах, а")))— попытка закрыть строковый литерал и скобки, чтобы внедрить свой код.AND EXTRACTVALUE(6676,CONCAT(0x7e,((SELECT (ELT(6676=6676,1)))),0x7e))— это и есть полезная нагрузка. ФункцияEXTRACTVALUEполучает два аргумента: первый — число 6676 (может быть любым), второй — результатCONCAT, который объединяет тильду (0x7e— шестнадцатеричный код символа ~), результат подзапроса и ещё одну тильду.SELECT (ELT(6676=6676,1))— это подзапрос, который возвращает 1, если условие6676=6676истинно. В реальной атаке вместо этого условия может быть любой запрос к базе, например, извлечение имени пользователя или хеша пароля.-- -— комментарий, который отсекает оставшуюся часть оригинального SQL-запроса, чтобы он не вызвал синтаксическую ошибку.
Когда MySQL выполняет EXTRACTVALUE с аргументом, содержащим символ ~ (тильда), функция пытается интерпретировать его как XPath. Поскольку это невалидный XPath, генерируется ошибка вида XPATH syntax error: '~1~'. В этом сообщении и оказывается результат подзапроса — в примере это 1. Если вместо ELT(6676=6676,1) подставить, например, (SELECT version()), то в ошибке отобразится версия MySQL. Так злоумышленник может пошагово извлекать любые данные: имена таблиц, столбцов, логины, пароли.
Зачем используется ELT и условие 6676=6676?
Конструкция ELT(6676=6676,1) — это простейший способ вернуть константу 1. Функция ELT(N, str1, str2, ...) возвращает N-ю строку из списка. Если N=1, возвращается первая строка. В данном случае 6676=6676 — это выражение, которое всегда истинно (равно 1), поэтому ELT(1,1) вернёт 1. Это нужно для демонстрации работоспособности инъекции: если приложение уязвимо, в ответе появится ошибка с тильдами и единицей. В реальной атаке вместо этого примитивного условия подставляют подзапросы, извлекающие ценную информацию.
Число 6676 в первом аргументе EXTRACTVALUE может быть любым — оно не влияет на результат, но иногда используется для обхода простых фильтров. Главное — второй аргумент, который содержит вредоносный XPath.
Почему это опасно и как защититься
Error-based SQL-инъекции через EXTRACTVALUE (а также через UPDATEXML) — один из самых быстрых способов получения данных из уязвимой базы MySQL. Они не требуют слепого перебора и часто срабатывают даже при минимальном выводе ошибок. Основная причина уязвимости — недостаточная фильтрация пользовательского ввода и конкатенация SQL-запросов вместо параметризации.
Чтобы защититься, необходимо:
- Использовать подготовленные выражения (prepared statements) с параметрами. Это самый надёжный способ, так как данные не попадают в текст запроса.
- Экранировать специальные символы при невозможности использовать параметризацию. Но этот метод менее надёжен.
- Отключить вывод подробных ошибок MySQL на продакшене. Это не устраняет уязвимость, но затрудняет эксплуатацию error-based инъекций.
- Ограничить права пользователя БД, от имени которого работает приложение. Не давайте ему доступ к системным таблицам.
- Использовать WAF (Web Application Firewall) для блокировки подозрительных запросов, содержащих
EXTRACTVALUE,UPDATEXMLи другие опасные функции.
Важно понимать, что EXTRACTVALUE — это лишь инструмент. Сама по себе функция не является уязвимостью; уязвимость возникает, когда злоумышленник может внедрить произвольный SQL-код в запрос. Поэтому главный совет: никогда не доверяйте пользовательскому вводу и всегда используйте параметризованные запросы.
Пример безопасного кода на PHP
Вместо конкатенации:
$query = "SELECT * FROM users WHERE name = '" . $_GET['name'] . "'";
Используйте подготовленные выражения:
$stmt = $pdo->prepare("SELECT * FROM users WHERE name = :name");
$stmt->execute(['name' => $_GET['name']]);
Такой подход полностью исключает возможность SQL-инъекции, включая error-based через EXTRACTVALUE.
Заключение
Строка %"))) AND EXTRACTVALUE(6676,CONCAT(0x7e,((SELECT (ELT(6676=6676,1)))),0x7e))-- - — это учебный пример эксплуатации error-based SQL-инъекции в MySQL. Она демонстрирует, как с помощью встроенной функции EXTRACTVALUE и намеренно вызванной ошибки можно получить данные из базы. Понимание этого механизма помогает разработчикам осознать важность защиты: параметризации запросов, отключения вывода ошибок и минимизации прав доступа к БД. Если вы нашли такую строку в логах своего сайта — это признак попытки взлома, и необходимо срочно проверить код на наличие уязвимостей.
Комментарии
—Войдите, чтобы оставить комментарий