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

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

Подобные строки часто встречаются в логах веб-серверов, в отчётах систем обнаружения вторжений (IDS) и в базах уязвимостей. Они не являются частью легитимного кода — это попытка атакующего внедрить свой SQL-код в запрос, который выполняет сайт.

Разбор по частям

Давайте разберём каждый элемент конструкции.

1. AND

Логический оператор, который добавляется к существующему условию WHERE в SQL-запросе. Атакующий предполагает, что исходный запрос выглядит примерно так: SELECT ... FROM ... WHERE id = 1 AND .... Добавляя AND, он пытается «приклеить» своё выражение, не нарушая синтаксис.

2. EXTRACTVALUE(7944, ...)

EXTRACTVALUE() — это встроенная функция MySQL (до версии 8.0), предназначенная для извлечения значения из XML-документа по заданному XPath-выражению. Синтаксис: EXTRACTVALUE(XML_document, XPath_expression).

Первый аргумент 7944 — просто число, которое интерпретируется как XML-фрагмент (некорректный, но это неважно). Второй аргумент — выражение, которое должно быть путём XPath. Если оно не является корректным XPath, MySQL генерирует ошибку XPATH syntax error, и в тексте ошибки отображается переданное значение. Именно на этом строится атака: злоумышленник может подставить в XPath результат подзапроса и увидеть его в сообщении об ошибке.

3. CONCAT(0x7e, ..., 0x7e)

CONCAT() объединяет строки. Здесь 0x7e — это шестнадцатеричное представление символа ~ (тильда). Тильда используется как маркер, чтобы в выводе ошибки было легко найти начало и конец извлечённых данных. Например, ошибка может выглядеть так: XPATH syntax error: '~данные~'.

4. (SELECT (ELT(7944=7944,1)))

Вложенный подзапрос. ELT(N, str1, str2, ...) возвращает N-ю строку из списка. Здесь 7944=7944 — всегда истинное условие, которое в MySQL даёт 1. Значит, ELT(1, 1) вернёт строку '1'. В реальной атаке вместо 1 подставляется подзапрос, извлекающий нужные данные, например: (SELECT version()) или (SELECT password FROM users LIMIT 1). В нашем примере это просто демонстрация синтаксиса.

5. -- -

Комментарий в SQL. Два дефиса с пробелом (или -- -) заставляют MySQL игнорировать всё, что идёт дальше в исходном запросе. Это нужно, чтобы «отрезать» возможные остатки оригинального SQL-кода (например, закрывающую кавычку или дополнительные условия) и не вызвать синтаксическую ошибку.

Как это работает на практике

Предположим, на сайте есть страница product.php?id=1, и в коде выполняется запрос:

SELECT * FROM products WHERE id = 1

Атакующий подставляет вместо 1 строку:

1 AND EXTRACTVALUE(7944,CONCAT(0x7e,(SELECT version()),0x7e))-- -

Итоговый запрос становится:

SELECT * FROM products WHERE id = 1 AND EXTRACTVALUE(7944,CONCAT(0x7e,(SELECT version()),0x7e))-- -

MySQL пытается выполнить EXTRACTVALUE, второй аргумент которого — не корректный XPath, а строка вида ~5.7.42~. Возникает ошибка:

XPATH syntax error: '~5.7.42~'

Эта ошибка возвращается в браузер (если включён вывод ошибок), и атакующий видит версию СУБД. Меняя подзапрос, он может извлекать имена таблиц, столбцов, логины, пароли и другие данные.

Почему это опасно

  • Утечка данных: через ошибки можно получить содержимое базы.
  • Обход аутентификации: иногда инъекция позволяет войти под администратором.
  • Полный контроль над БД: в некоторых случаях — чтение и запись файлов, выполнение команд.

Error-based инъекции особенно удобны для атакующего, потому что не требуют слепого перебора: сервер сам «рассказывает» данные в тексте ошибки.

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

  1. Используйте подготовленные выражения (prepared statements). Это самый надёжный способ: параметры запроса передаются отдельно от SQL-кода, и внедрить что-либо в структуру запроса невозможно.
  2. Экранируйте пользовательский ввод. Если подготовленные выражения недоступны, применяйте функции экранирования, соответствующие вашей СУБД (например, mysqli_real_escape_string).
  3. Отключите вывод ошибок на продакшене. Сообщения об ошибках должны писаться в лог, а не показываться пользователю.
  4. Ограничьте права пользователя БД. Приложению не нужны права DROP или FILE.
  5. Используйте WAF. Веб-application firewall может отфильтровать типовые сигнатуры атак, включая EXTRACTVALUE и CONCAT(0x7e.

Контекст: где встречается эта строка

Подобные payload'ы часто попадают в логи при сканировании сайтов уязвимостями (например, сканерами вроде sqlmap). Иногда их можно увидеть в отчётах хостинг-провайдеров или в системах мониторинга. Если вы нашли такую строку в логах своего сайта — это признак того, что кто-то пытался проверить ваш ресурс на наличие SQL-инъекций. Стоит проверить код на уязвимости и убедиться, что все запросы к БД параметризованы.

Важно понимать: сама по себе строка AND EXTRACTVALUE(7944,CONCAT(0x7e,((SELECT (ELT(7944=7944,1)))),0x7e))-- - не является «вредоносной программой» — это просто текст, который может быть использован как часть атаки. Но если сервер уязвим, она может привести к утечке данных.

Краткий итог

Мы разобрали, что запрос AND EXTRACTVALUE(7944,CONCAT(0x7e,((SELECT (ELT(7944=7944,1)))),0x7e))-- - — это пример error-based SQL-инъекции для MySQL. Он использует функцию EXTRACTVALUE для вызова ошибки, в текст которой подставляются данные из подзапроса. Символ 0x7e служит маркером, а -- - комментирует остаток запроса. Защита — это подготовленные выражения, отключение вывода ошибок и грамотное разграничение прав.

Источники