Безопасен ли std:: конструктор регулярных выражений?

#c

#c

Вопрос:

Просто чтобы убедиться:
Конструкторы std::basic_regex должны обнаруживать недопустимые выражения и выдавать исключение, если оно неверно. Верно? Итак, предполагая, что я доверяю своему разработчику STL, я могу передать ему строки произвольного выражения, и я получу либо допустимый объект регулярных выражений, либо исключение — без UB или что-то в этом роде?

Кто-нибудь знает о глючных std::basic_regex реализациях (EDIT: или других частях библиотеки регулярных выражений), которые не защищены от ошибочных входных данных?

Комментарии:

1. Это то, о чем говорится в документации regex . Однако ни одна реализация не является полностью свободной от ошибок. Есть ли какая-то конкретная реализация, которая вас беспокоит?

2. @P.W: Ну, обычные, такие как msvc, libstdc и libc . По сути, мне интересно, можно ли напрямую передавать в него пользовательские данные без какой-либо очистки (не беспокоясь о безопасности — просто надежность)

3. у libstdc действительно есть проблемы: Смотрите один пример: gcc.gnu.org/bugzilla/show_bug.cgi?id=86164

4. Так же, как и libc : bugs.llvm.org/show_bug.cgi?id=23017

5. Обратите внимание, что последний параметр во всех пяти конструкторах, которые могут представлять интерес в данном случае, определяет используемую грамматику регулярных выражений и по умолчанию используется ECMAScript.

Ответ №1:

Предполагая, что в стандартных библиотеках нет ошибок (они есть, как указано P.W), существует более общая атака, называемая ReDoS, как описано в OWASP:

Отказ в обслуживании регулярных выражений (ReDoS) — это атака типа «Отказ в обслуживании», которая использует тот факт, что большинство реализаций регулярных выражений могут достигать экстремальных ситуаций, которые заставляют их работать очень медленно (экспоненциально в зависимости от размера входных данных). Затем злоумышленник может заставить программу, использующую регулярное выражение, попасть в эти экстремальные ситуации, а затем зависнуть на очень долгое время.

Поэтому я бы, по крайней мере, ограничил размер разрешенного ввода, чтобы ваша программа не могла быть выполнена. Во-вторых, общий подход к проверке надежности движка заключается в фаззинге. Существует множество библиотек фаззинга и некоторые проекты на GitHub, которые содержат «непослушные» строки, явно предназначенные для перьевого тестирования. Возможно, вам покажется целесообразным разделить различные движки, чтобы увидеть, где они выходят из строя.

Комментарии:

1. Введение некоторых базовых ограничений, безусловно, имело бы смысл. Хотя, как я упоминал в комментарии, меня на самом деле не интересует безопасность. Если пользователь (обычно я сам) хочет намеренно завершить работу приложения, это его прерогатива ;).