Уязвимость усечения SQL обычно существует в базах данных MySQL. Эта уязвимость была впервые описана в CVE-2008-4106, который относился к WordPress CMS.
Как работают атаки усечения SQL
Эта атака работает из-за усечения пользовательского ввода в базах данных с помощью функций «выбора» и «вставки».
- Когда ввод задан в поле формы, функция select проверяет избыточность, соответствующую вводам в базе данных.
- После проверки избыточности функция вставки проверяет длину ввода, и ввод пользователя будет обрезан, если длина превышает.
Предположим, что разработчик создает таблицу «пользователей» с помощью следующего запроса:
создать таблицу пользователей (user_id INT NOT NULL AUTO_INCREMENT,
имя_пользователя VARCHAR (20) NOT NULL,
пароль VARCHAR (40) NOT NULL,
ПЕРВИЧНЫЙ КЛЮЧ (user_id)
);
Используя эту схему, если разработчик создает учетную запись администратора со следующим:
user_name = 'админ'пароль = «secret_p4ssw0ord»
Очевидно, эти учетные данные не являются общедоступными. В базе данных есть только одна учетная запись администратора, и если злоумышленник попытается зарегистрировать другую учетную запись с именем пользователя admin, злоумышленник потерпит неудачу из-за проверок избыточности базы данных. Злоумышленник может обойти эту проверку избыточности, чтобы добавить еще одну учетную запись администратора, используя уязвимость усечения SQL. Предположим, что злоумышленник регистрирует другую учетную запись со следующими данными:
Имя_пользователя = 'adminxxxxxxxxxxxxxxxrandom'(x - пробелы)
&
Пароль = "RandomUser"
База данных возьмет 'user_name' (26 символов) и проверит, существует ли оно уже. Затем ввод user_name будет усечен, и в базу данных будет введено 'admin' ('admin' с пробелом), в результате получатся два дублирующих пользователя admin.
Затем злоумышленник может создать пользователя с правами администратора со своим собственным паролем. Теперь в базе данных есть две записи admin 'user_name', но с разными паролями. Злоумышленник может войти в систему с вновь созданными учетными данными, чтобы получить панель администратора, потому что оба имени пользователя «admin» и «admin» равны для уровня базы данных. Теперь мы рассмотрим образец практической атаки.
Образец атаки
В этом примере мы возьмем сценарий с веб-сайта через Интернет.org. Сообщество Overthewire предоставляет CTF для варгеймов, на которых мы можем практиковать наши концепции безопасности. Сценарий усечения SQL происходит на уровнях игры natas 26-> 27. Мы можем получить доступ к уровню, используя следующее:
URL: http: // natas27.натас.лаборатории.через провод.orgИмя пользователя: natas27
Пароль: 55TBjpPZUUJgVP5b3BnbG6ON9uDPVzCJ
Этот уровень доступен по адресу: https: // overthewire.org / wargames / natas / natas27.html. Вам будет показана страница входа, которая уязвима для атаки усечения SQL.
Изучив исходный код, вы увидите, что длина имени пользователя равна 64, как показано ниже.
Пользователь с именем natas28 уже существует. Наша цель - создать еще одного пользователя с именем natas28 с помощью атаки SQL_truncation. Итак, мы введем natas28, затем 57 пробелов и случайный алфавит (в нашем случае a), имя пользователя и любой пароль. Буква 'a' не видна на скриншоте из-за 65-символьного имени пользователя. После создания учетной записи пользователя вы увидите значок 'а.'
Если база данных содержит уязвимость sql_truncation, то теперь в базе данных должно быть два имени пользователя natas28. Одно имя пользователя будет содержать наш пароль. Попробуем ввести учетные данные на странице входа.
Теперь мы вошли в систему как пользователь natas28.
Смягчение
Чтобы смягчить эту атаку, нам нужно будет рассмотреть несколько факторов.
- Мы не должны допускать дублирования важных идентификаторов, таких как имя пользователя. Мы должны сделать эти удостоверения первичными ключами.
- Функция усечения должна быть реализована для всех полей форм внешнего интерфейса, а также для внутреннего кода, чтобы базы данных получали усеченные входные данные.
- Строгий режим должен быть включен на уровне базы данных. Без включенного строгого режима базы данных выдают только предупреждения в бэкэнде, но при этом сохраняют дублированные данные. В строгом режиме базы данных выдают ошибки в случае дублирования и избегают сохранения данных.
Например, давайте проверим строгий режим, используя следующий запрос:
mysql> выберите @@ sql_mode
Создадим базу данных и таблицу пользователей.'
mysql> CREATE DATABASE testЗапрос в порядке, затронута 1 строка (0.02 сек)
mysql> Использовать тест
База данных изменена
mysql> CREATE TABLE пользователи (имя пользователя VARCHAR (10), пароль VARCHAR (10));
Запрос в порядке, затронуты 0 строк (0.05 сек)
Затем мы создадим пользователя-администратора с учетными данными с помощью запроса INSERT.
mysql> ВСТАВИТЬ В ЗНАЧЕНИЯ пользователей ('admin', 'password1');Запрос в порядке, затронута 1 строка (0.01 сек)
Мы можем увидеть информацию из таблицы «пользователи», используя опцию «выбрать * из пользователей».
Длина имени пользователя 10 символов. Теперь мы попробуем атаку усечения SQL.
Когда мы пытаемся ввести следующее:
Имя пользователя = 'adminxxxxxa'(x - пробелы)
&
Пароль = 'pass2'
Мы получим ошибку, означающую, что строгий режим полностью эффективен.
mysql> INSERT INTO значения пользователей ('admin a', 'pass2')ОШИБКА 1406 (22001): слишком длинные данные для столбца «имя пользователя» в строке 1
Без включенного строгого режима база данных будет выводить предупреждения, но все равно будет вставлять данные в таблицу.
Заключение
Злоумышленники могут получить доступ к учетным записям с высоким уровнем привилегий, если в вашем приложении существует уязвимость sql_trunction. Злоумышленник может легко получить информацию об имени пользователя и длине его базы данных, используя критические поля, затем создать такое же имя пользователя, за которым следуют пробелы и случайный алфавит после минимальной длины, что приведет к созданию нескольких учетных записей с высоким уровнем привилегий. Эта уязвимость является критической, но ее можно избежать, если принять некоторые меры безопасности, такие как активация строгого режима для пользовательского ввода и установка конфиденциального поля в качестве первичного ключа в базе данных.