Комментарии 17
строка копируется или записывается в буфер фиксированного размера без должной проверки длины строки.
Пипец какой-то.
Тут не про строки, тут про то, как сознательно убиться головой об стену.
100% защиты от дурака не существует - найдет лазейку и любую обойдет.
Я не понял, как третий пример (с `std::string`) решает проблему ловушки 1.
Если вы про пример со strncopy, то третьим параметром там передаётся размер целевого буфера, а не строки. Зачем там substring магической длины правда непонятно.
Привет Хабр! Меня зовут Владислав Столяров. Я аналитик безопасности продуктов в компании МойОфис.
Оффтопик, но зачем это нужно в статье? Как же бесят эти шаблонные куски у определенного подмножества авторов
Информация об авторе есть над статьей и под статьей. Если статья годная и я почитаю её до конца, я увижу имя автора. А в начале статьи эта информация зачем? Придать свои словам больший вес? Порекламировать контору?
QString вполне себе развивается. Входит в состав Qt Framework.
Юзайте std::string и не юзайте си наследие в виде printf, strcpy и т.д
И да прибудут с вами, новые стандарты С++.
У меня есть своя специфическая ошибка: в одной программе значение поля из результата запроса SQL преобразовывалось в std::string без проверки на нулевой указатель. Мы знали: если программа на старте падает, значит таблица сломалась, и из неё читаются значения NULL.
Что за ловушки? Кого они ловят?
4 примера говнокода, которые были актуальны 20 лет назад? Ну ок.
Для начала, в 2024 году надо прекратить писать статьи про C++, приводя внутри чисто сишный код. Потом можно задуматься о том, что строки в плюсах бывают разными. А ещё можно не высасывать примеры из одного места. Функция поиска не может возвращать бул, она может возвращать индекс, итератор, но не бул. Как функция поиска может возвращать что-то другое? Логика вышла из чата.
В случае неудачи, функции возвращают статическую константу npos.
Когда хотел написать что-то умное, а получилось... Функция возвращает индекс, а если вхождение не найдено, то возвращает -1, он же npos в виде unsigned. Интуитивно понятно, и не надо пытаться высасывать примеры.
У нас остался последний пример, с потоком ввода? Интересно, а какое отношение сия проблема имеет к строкам и вообще плюсам? Правильно, никакого. Проверка ввода - сложная и нетривиальная задача. Но надо ж что-то высосать аналитику
В исправленном коде ... Также мы увеличили размер буфера на 1 и установили
нуль-терминатор в конце буфера, чтобы гарантировать корректное
завершение строки.
В третьем примере буфер не увеличили на 1, как был buffer[10], так и остался. И нулевого символа в конце все равно не будет.
А если говорить вообще, то смешивать С и С++ код - плохая практика.
Еще можно добавить, что strlen(NULL)
, вызывает SEGFAULT, хотя этого в мане не описано
Если бы ты внимательно читал стандарт, ты не писал бы таких глупостей.
Что должно подаваться на вход strlen()? Указатель на строку. Это в мане написано. Что такое строка в С? Массив символов (возможно, пустой), терминированный нулевым символом. Каким образом NULL является указателем на строку? Никаким. Annex J стандарта информирует, что поведение компилятора в таких случаях не определено. А ты ничем не отличаешься от тех суровых сибирских мужиков из анекдота, которые продемонстрировали, что японская лесопилка — отстой, засунув в неё стальной лом.
Мне лет 20 назад один программист из Индии продемонстрировал ещё одну похожую уязвимость: char* a = strdup(NULL);
Он так пустую строку создавал :-) Это я к тому, что главный способ обезопасить код - это не допускать к его написанию неграмотных программеров и писать unit test'ы. Что до серьёзных уязвимостей в том же С - есть специальные многостраничные документы, выпущенные на этот счёт серьёзными людьми. Всё приведённое в статье, отлавливается PVSC, например. Ну и всегда указывать в опциях компилятора wall...
Нулевой символ в С строке точно называется EOL?))
В современном C++ советуют использовать везде где можно string_view вместо const char*. Но и с ним возможен прострел ноги.
void Foo(std::string_view s)
{
std::printf("s is %s", s.data());
}
4 типовые ловушки в работе со строками в С и С++ и как их избежать