Что это за строка?
Перед нами типичный пример SQL-инъекции (SQL injection) — атаки, при которой злоумышленник внедряет вредоносный SQL-код в запрос к базе данных. Конкретная строка )) AND EXTRACTVALUE(6693,CONCAT(0x7e,((SELECT (ELT(6693=6693,1)))),0x7e))-- - представляет собой эксплойт, нацеленный на СУБД MySQL. Он использует встроенные функции EXTRACTVALUE и CONCAT для выполнения подзапроса и вывода его результата в сообщении об ошибке. Такой метод называется error-based SQL injection (инъекция, основанная на ошибках).
Разбор компонентов инъекции
Давайте разберём строку по частям, чтобы понять логику атакующего.
))— закрывающие скобки, которые «ломают» исходный запрос, чтобы внедрить свой код. Обычно используются, когда оригинальный запрос содержит подзапрос или функцию.AND— логический оператор, позволяющий присоединить дополнительное условие.EXTRACTVALUE(6693, CONCAT(...))— функция MySQL, которая извлекает значение из XML-документа по XPath-выражению. Если второй аргумент не является корректным XPath, функция выдаёт ошибку, в текст которой попадает переданная строка.6693— произвольное число (идентификатор), которое не несёт смысловой нагрузки, но должно быть допустимым первым аргументом.CONCAT(0x7e, ((SELECT (ELT(6693=6693,1)))), 0x7e)— конкатенация символа тильды (0x7eв шестнадцатеричном виде), результата подзапроса и ещё одной тильды. Тильды используются как маркеры, чтобы облегчить извлечение данных из сообщения об ошибке.(SELECT (ELT(6693=6693,1)))— подзапрос, который возвращает строку.ELT(N, str1, str2, ...)возвращает N-ю строку из списка. Здесь6693=6693всегда истинно (1), поэтомуELT(1,1)вернёт «1». В реальной атаке вместо этого подзапроса мог бы быть, например,(SELECT password FROM users LIMIT 1).-- -— комментарий, который «отрезает» оставшуюся часть оригинального запроса, чтобы синтаксис стал корректным.
Таким образом, внедрённый код заставляет базу данных выполнить подзапрос (в данном случае возвращающий число 1), обернуть результат в тильды и попытаться передать его в EXTRACTVALUE как XPath. Поскольку строка с тильдами не является допустимым XPath, MySQL сгенерирует ошибку примерно такого содержания: XPATH syntax error: '~1~'. Из этой ошибки атакующий может прочитать результат подзапроса.
Цель инъекции
Основная цель — получить возможность выполнять произвольные SQL-запросы и извлекать данные из базы. В данном примере подзапрос возвращает константу, но в реальной атаке на его место подставляются запросы к таблицам (например, SELECT username FROM users LIMIT 1). Использование EXTRACTVALUE позволяет обойти ограничения, когда приложение не выводит данные напрямую, но отображает сообщения об ошибках базы данных. Это один из классических методов, описанных в многочисленных руководствах по SQL-инъекциям.
Как работает EXTRACTVALUE в MySQL
Функция EXTRACTVALUE(XMLType_instance, XPath_expression) появилась в MySQL 5.1. Она принимает XML-документ и выражение XPath, возвращая текст узла. Если XPath-выражение некорректно, функция вызывает ошибку, которая включает переданное выражение. Именно это свойство и эксплуатируется: злоумышленник формирует XPath, содержащий полезную нагрузку (результат подзапроса), и провоцирует ошибку, чтобы прочитать данные. Стоит отметить, что в MySQL 8.0.17 и выше функция EXTRACTVALUE объявлена устаревшей (deprecated), однако на момент написания статьи она всё ещё доступна во многих установках.
Пример уязвимого запроса
Предположим, в приложении есть такой запрос:
SELECT * FROM products WHERE id = '$id';Если параметр $id не экранируется, атакующий может подставить нашу строку, и запрос превратится в:
SELECT * FROM products WHERE id = '')) AND EXTRACTVALUE(6693,CONCAT(0x7e,((SELECT (ELT(6693=6693,1)))),0x7e))-- -';В результате база данных выполнит внедрённое условие и вернёт ошибку с внедрёнными данными. В реальной атаке вместо ELT(6693=6693,1) будет стоять подзапрос, извлекающий, например, имя пользователя и пароль.
Как защититься от таких инъекций
Основной способ защиты — использование параметризованных запросов (prepared statements). При этом данные передаются отдельно от SQL-кода, и внедрение становится невозможным. Дополнительные меры:
- Экранирование специальных символов (хотя это менее надёжно, чем параметризация).
- Ограничение прав пользователя базы данных: приложение должно работать с минимально необходимыми привилегиями.
- Отключение вывода подробных сообщений об ошибках базы данных в production-среде.
- Регулярное обновление СУБД и применение патчей безопасности.
- Использование веб- application firewall (WAF) для фильтрации подозрительных запросов.
Важно понимать, что подобные строки часто встречаются в логах веб-серверов как попытки сканирования уязвимостей. Если вы видите такую запись, это может означать, что ваш сайт пытались взломать. Необходимо проверить код на наличие уязвимостей и убедиться, что все запросы к базе данных используют параметризацию.
Заключение
Строка )) AND EXTRACTVALUE(6693,CONCAT(0x7e,((SELECT (ELT(6693=6693,1)))),0x7e))-- - — это не случайный набор символов, а тщательно сконструированный эксплойт для error-based SQL-инъекции в MySQL. Понимание его работы помогает разработчикам и специалистам по безопасности лучше защищать свои приложения. Никогда не доверяйте пользовательскому вводу и всегда используйте параметризованные запросы.
Комментарии
—Войдите, чтобы оставить комментарий