Что такое SQL-инъекция через EXTRACTVALUE?
SQL-инъекция — один из самых распространённых способов взлома веб-приложений. Злоумышленник вставляет вредоносный код в SQL-запрос, который выполняется на сервере. В данном случае используется функция EXTRACTVALUE — встроенная функция MySQL для работы с XML. Она извлекает значение из XML-документа по заданному XPath-выражению. Если передать в неё некорректный XPath, MySQL выдаст ошибку, которая может содержать результаты выполнения вложенного запроса. Это называется error-based SQL-инъекцией.
Запрос %') AND EXTRACTVALUE(1422,CONCAT(0x7e,((SELECT (ELT(1422=1422,1)))),0x7e))-- - — это классический пример внедрения в параметр, который подставляется в SQL-запрос без должной фильтрации.
Разбор синтаксиса запроса
Давайте разберём каждую часть этого запроса по порядку.
- %') — закрывает предыдущее выражение в исходном запросе. Символ
%часто используется в LIKE-запросах, а')закрывает скобку и кавычку, завершая строковый литерал. - AND — логический оператор, добавляющий условие к оригинальному запросу.
- EXTRACTVALUE(1422, CONCAT(...)) — вызов функции. Первый аргумент (1422) — это XML-документ (фактически число, которое будет преобразовано в XML). Второй аргумент — XPath-выражение, которое формируется динамически через CONCAT.
- CONCAT(0x7e, ((SELECT (ELT(1422=1422,1)))), 0x7e) — конкатенация символа
~(0x7e), результата подзапроса и снова~. - SELECT (ELT(1422=1422,1)) — подзапрос, который возвращает 1. Функция ELT возвращает N-й элемент из списка. Здесь
1422=1422— всегда истина, поэтому ELT(1,1) вернёт 1. - -- - — комментарий, который обрезает оставшуюся часть оригинального запроса, чтобы не возникло синтаксической ошибки.
Как работает атака
Когда этот код попадает в SQL-запрос, сервер выполняет EXTRACTVALUE. Второй аргумент — строка вида ~1~. Это невалидный XPath, поэтому MySQL генерирует ошибку: XPATH syntax error: '~1~'. В сообщении об ошибке отображается переданная строка. Если вместо константы 1 подставить подзапрос, извлекающий данные (например, имя пользователя или хеш пароля), то эти данные попадут в текст ошибки и будут видны атакующему.
В данном конкретном примере подзапрос возвращает просто 1, что демонстрирует работоспособность метода. На практике злоумышленник заменил бы 1 на (SELECT password FROM users LIMIT 1) и получил бы пароль в сообщении об ошибке.
Зачем нужен CONCAT и 0x7e?
Символ ~ (тильда) используется как маркер, чтобы облегчить извлечение данных из сообщения об ошибке. XPath-парсер MySQL выводит ошибку в формате: XPATH syntax error: 'значение'. Тильды помогают быстро найти начало и конец полезной нагрузки. CONCAT собирает все части в одну строку, которая затем передаётся как XPath.
Функция ELT и её роль
ELT(N, str1, str2, ...) возвращает N-й элемент из списка строк. В нашем случае ELT(1422=1422, 1) — условие 1422=1422 всегда истинно (возвращает 1), поэтому ELT(1,1) вернёт первый элемент — 1. Это простой способ получить константу. В более сложных атаках ELT может использоваться для перебора данных по индексу.
Какие уязвимости эксплуатирует запрос?
Основная причина — отсутствие параметризации запросов. Если веб-приложение подставляет пользовательский ввод напрямую в SQL-строку, оно уязвимо. Конкретно здесь эксплуатируется:
- Некорректная обработка спецсимволов (кавычки, скобки).
- Отсутствие экранирования.
- Использование устаревших функций MySQL, которые не отключены (EXTRACTVALUE доступна, но помечена как deprecated в MySQL 5.7+).
Как защититься от таких инъекций?
Вот основные меры:
- Параметризованные запросы (prepared statements). Это самый надёжный способ. Данные передаются отдельно от SQL-кода, и внедрение становится невозможным.
- Экранирование специальных символов. Если параметризация невозможна, используйте функции экранирования (например, mysqli_real_escape_string).
- Валидация входных данных. Проверяйте, что вводимые данные соответствуют ожидаемому формату (число, email и т.д.).
- Отключение опасных функций. Если EXTRACTVALUE не используется в приложении, её можно отключить или ограничить права пользователя БД.
- Использование ORM. Современные ORM (например, Doctrine, Hibernate) автоматически параметризуют запросы.
- Регулярные аудиты безопасности. Сканеры уязвимостей помогут выявить SQL-инъекции.
Заключение
Запрос %') AND EXTRACTVALUE(1422,CONCAT(0x7e,((SELECT (ELT(1422=1422,1)))),0x7e))-- - — это учебный пример error-based SQL-инъекции. Он показывает, как через ошибки MySQL можно извлекать данные. Понимание таких атак помогает разработчикам писать безопасный код и защищать веб-приложения.
Комментарии
—Войдите, чтобы оставить комментарий