Я разборщик stackoverflow дампа и подошел к this, казалось бы, невинный вопрос с маленькой, почти невидимой деталью, что у него 22311 пробелов в конце текста.С ++ regex segfault на длинных последовательностях
Я использую зЬй :: регулярное выражение (как-то они работают лучше для меня, чем повышение :: регулярное выражение), чтобы заменить все непрерывные пробельные единое пространство, как это:
std::regex space_regex("\\s+", std::regex::optimize);
...
std::regex_replace(out, in, in + strlen(in), space_regex, " ");
SIGSEGV показывает, и у меня есть начал расследование.
код теста:
#include <regex>
...
std::regex r("\\s+", std::regex::optimize);
const char* bomb2 = "Small text\n\nwith several\n\nlines.";
std::string test(bomb2);
for (auto i = 0; i < N; ++i) test += " ";
std::string out = std::regex_replace(test.c_str(), r, " ");
std::cout << out << std::endl;
для (GCC 5.3.0)
$ g++ -O3 -std=c++14 regex-test.cpp -o regex-test.out
максимум N
перед тем SIGSEGV показывает вверх является 21818 (для этой конкретной строки), а также для
$ g++ -O0 -std=c++14 regex-test.cpp -o regex-test.out
его 12180.
«Хорошо, давайте попробуем заговорить, это тренда и цель заменить gcc» - никогда бы я не ошибся. С -O0
clang (v. 3.7.1) падает на 9696 пробелов - меньше, чем gcc, но не очень, но с -O3
и даже с -O2
он падает на пространства ZERO.
Краш свалка представляет огромные stacktraces (35K кадров) рекурсивных вызовов
std::__detail::_Executor<char*, std::allocator<std::__cxx11::sub_match<char*> >, std::__cxx11::regex_traits<char>, true>::_M_dfs
Вопрос 1: Является ли это ошибка? Если да, я должен сообщить об этом?
Вопрос 2: Есть ли способ преодолеть проблему (кроме увеличения размера системного стека, попытки других библиотек регулярных выражений и записи собственных функций для замены пробелов)?
Поправка:bug report создан для libstdC++
Ваш тестовый код [корректно работает с лязгом, если опция компилятора -stdlib = LibC++ используется] (http://coliru.stacked-crooked.com/a/91ffcf96e925b2a3). Скорее всего, это ошибка в libstdC++ – cpplearner