The Daily Newsstand · Free, Always
Wednesday, November 4, 2026

Rust и C++: анализ официальных документов CISA, NSA, Google и Microsoft

Translate

Здравствуйте. Прежде всего прошу отнестись к статье объективно: подобные темы часто вызывают холивары, и я такое осуждаю. Цель статьи — обзор, почему мировые организации стремятся перейти на Rust.

Прежде чем начать обзор, приведу документы от разных организаций. Рекомендую с ними ознакомиться, а если вам лень — чуть ниже я кратко расскажу, о чём они. Часть моих выводов основана на анализе документов мировых организаций, цель которых — либо безопасность общества, либо приумножение прибыли.

  • Совместный отчёт CISA и NSA (июнь 2025) «Memory Safe Languages: Reducing Vulnerabilities in Modern Software Development» — [1], [2].

  • Декабрь 2023 года: CISA, FBI, NSA и международные партнёры опубликовали масштабное совместное руководство «The Case for Memory Safe Roadmaps» — [3].

  • Google Security Blog — “Rust in Android: move fast and fix things” — [4].

Исторически около 70% уязвимостей в продуктах Microsoft были связаны с безопасностью памяти (по данным за 2006–2018 годы). Информация о повышении статуса Rust до уровня Tier-1 для внутренней разработки в Microsoft подтверждается официальным блогом Rust Foundation. Microsoft также активно продвигает Rust для разработки драйверов Windows, что подтверждается официальными блогами и релизами инструментов.

О чём были документы

Первый документ начинается с сильнейшего заявления: «Важность безопасности памяти невозможно переоценить». Основная мысль заключается в том, что десятилетия практики «безопасного кодирования» и использования внешних анализаторов кода не смогли решить проблему. Отчёт констатирует, что такие инструменты не могут полностью устранить уязвимости, присущие языкам вроде C и C++. Поэтому документ предлагает фундаментальный сдвиг: перенести бремя безопасности с дисциплины разработчика на сам язык программирования. Безопасные языки (MSL) встраивают защитные механизмы (проверка границ, управление памятью, предотвращение гонок данных) непосредственно в язык, что делает их безопасными по дизайну (secure by design).

Отчёт подкрепляет выводы статистикой, демонстрирующей, что проблема безопасности памяти — это не теоретический риск, а основной вектор реальных атак. Согласно данным Google Project Zero, упомянутым в отчёте, 75% CVE, которые эксплуатируются в реальных атаках, связаны с ошибками памяти. Пример Microsoft: по данным за 2006–2018 годы, около 70% уязвимостей были связаны с безопасностью памяти.

Одной из сильных сторон отчёта является то, что он открыто признаёт проблемы, с которыми сталкиваются организации при переходе. Технические барьеры: нехватка необходимых сторонних библиотек и инструментов, проблемы с управлением зависимостями, а также возможное снижение производительности из‑за накладных расходов на взаимодействие между кодом на MSL и не‑MSL (interlanguage communication). Организационные и финансовые барьеры: необходимость значительных первоначальных инвестиций в инструменты, обучение и рефакторинг. Отчёт признаёт, что экономия (за счёт снижения числа уязвимостей) проявится не сразу, и её будет сложно измерить напрямую.

Второй документ приводит статистику, чтобы обосновать необходимость действий на уровне руководства. Около двух третей всех сообщаемых уязвимостей в языках, небезопасных для памяти, по‑прежнему связаны с проблемами управления памятью. В документе приводятся данные, что около 70% CVE в Microsoft (на основе данных 2006–2018 гг.) и в проекте Chromium от Google связаны с безопасностью памяти. Анализ уязвимостей Mozilla показал, что 32 из 34 критических ошибок были связаны с памятью. По данным Google Project Zero, 67% zero‑day уязвимостей в 2021 году относились к этой категории.

Авторы документа признают, что разработчики десятилетиями пытались смягчить проблему с помощью различных методов: обучения, покрытия кода тестами, фаззинга, статического и динамического анализа (SAST/DAST), использования «безопасных подмножеств» языка (например, для C++) и различных техник защиты во время выполнения (ASLR, sandboxing, hardening аллокаторов). Однако, несмотря на эти усилия, безопасность памяти остаётся ведущей причиной уязвимостей. Документ объясняет это тем, что данные методы либо не могут найти все ошибки, либо являются обходными путями, которые не устраняют корень проблемы. Вывод: единственный способ действительно искоренить этот класс уязвимостей — перейти на языки, которые гарантируют безопасность памяти на уровне дизайна (Memory Safe Languages, MSLs). «The Case for Memory Safe Roadmaps» — это практическое руководство к действию. Оно переводит проблему безопасности памяти из абстрактной технической плоскости в область стратегического управления и бизнес‑планирования.

Третий документ представляет собой подробный отчёт о результатах внедрения Rust в Android за прошедший год. Его главный тезис: переход на Rust не только радикально повысил безопасность, но и, что стало неожиданностью, ускорил и упростил процесс разработки. Автор поста, Джефф Вандер Ступ (Jeff Vander Stoep) из команды Android, строит повествование вокруг данных, которые подтверждают, что «безопасный путь теперь ещё и более быстрый».

Главное достижение, о котором сообщается в документе, — рекордное снижение доли уязвимостей, связанных с безопасностью памяти. В 2025 году доля таких уязвимостей в Android впервые упала ниже 20% от общего числа. Google также заявляет о 1000-кратном снижении плотности уязвимостей памяти в коде на Rust по сравнению с кодом на C и C++ в Android. Плотность уязвимостей для Rust оценивается в 0.2 на миллион строк кода (MLOC), в то время как исторические данные для C/C++ показывают около 1000 уязвимостей на MLOC.

Одним из самых значимых открытий стало то, что Rust не просто безопаснее, но и выгоднее с точки зрения инженерных ресурсов. Для оценки использовалась методика DORA (DevOps Research and Assessment) — стандарт в индустрии для измерения производительности команд. Количество откатов изменений (rollback rate) для Rust примерно в 4 раза ниже, чем для C++. Это критически важно, так как откаты — это дорогостоящие сбои, которые отнимают ресурсы и время у всей команды. Изменения на Rust требуют примерно на 25% меньше времени на код‑ревью. Rust‑код также требует примерно на 20% меньше ревизий по сравнению с аналогичным по размеру кодом на C++.

Документ также рассказывает о «почти случившейся» первой уязвимости в Rust‑коде — инциденте в парсере изображений CrabbyAVIF. Ошибка (переполнение буфера) была обнаружена и исправлена до публичного релиза, но ей всё равно был присвоен идентификатор CVE-2025-48530 для отслеживания. Этот случай используется для важного: даже в unsafe‑блоках Rust риски значительно ниже. Google объясняет это несколькими факторами: unsafe не отключает все проверки безопасности языка; практика инкапсуляции unsafe‑кода в безопасные абстракции позволяет рассуждать о безопасности локально; unsafe‑блоки привлекают повышенное внимание при ревью.

А теперь самое интересное: какое же отличие Rust от C++ дало такое преимущество с сохранением производительности?

Система владения (Ownership). В C++ ответственность за освобождение памяти и отслеживание времени жизни объектов лежит на программисте. Rust вводит строгие правила, проверяемые на этапе компиляции: у каждого значения есть ровно один владелец; когда владелец выходит из области видимости, значение автоматически освобождается (детерминированно, как в C++, но без ручного управления); передача значения в функцию перемещает владение, а не копирует его.

Заимствование (Borrowing) и «деструктивное перемещение». Заимствование позволяет временно использовать значение, не передавая владение. Здесь проявляется ещё одно важное отличие — семантика перемещения (move semantics). В C++ перемещение объекта оставляет его в «валидном, но неопределённом состоянии» (обычно пустом), и для него всё равно должен вызываться деструктор. Это создаёт накладные расходы и потенциальные ловушки. В Rust перемещение является деструктивным (побитовым): байты просто копируются в новое место, а исходная переменная считается недействительной на уровне компилятора. Деструктор для неё не вызывается. Это не только безопаснее, но и эффективнее: генерируется более простой и оптимизируемый машинный код (например, Vec::pop() или Option::take() работают быстрее).

«Нулевая стоимость» абстракций и неявные гарантии для оптимизатора. Это, пожалуй, самый прямой ответ на вопрос о производительности. Rust следует принципу «zero‑cost abstractions»: высокоуровневые конструкции (итераторы, замыкания, дженерики) не должны добавлять накладных расходов во время выполнения по сравнению с ручным низкоуровневым кодом. Но самое интересное — как это работает под капотом. Система владения и заимствования даёт компилятору Rust информацию, которую компилятор C++ получить не может. &mut T (изменяемая ссылка) гарантированно уникальна: компилятор знает, что никакая другая ссылка не указывает на эти данные одновременно. Это эквивалент ключевого слова restrict в C, но применяемый автоматически и повсеместно. &T (разделяемая ссылка) гарантированно неизменяема: компилятор знает, что данные не могут измениться, пока существует эта ссылка. В C++ const_cast может нарушить это обещание, поэтому оптимизатор вынужден быть консервативным. Благодаря этим гарантиям LLVM (бэкенд компилятора Rust) может применять более агрессивные и безопасные оптимизации, такие как лучшее размещение в регистрах и устранение лишних загрузок из памяти. Согласно одному исследованию на реальных драйверах, тщательно оптимизированный безопасный код на Rust достигал 93% пропускной способности небезопасного C, что делает разрыв в производительности минимальным.

Предсказуемая обработка ошибок. В C++ исключения (exceptions) являются основным механизмом обработки ошибок, но они несут скрытые расходы (таблицы размотки стека) и усложняют написание кода, безопасного относительно исключений (exception‑safe code). Rust использует типы Result<T, E> и Option для явного возврата ошибок. Это делает поток управления предсказуемым и не требует runtime‑поддержки в виде размотки стека. Хотя это может показаться многословным, это даёт компилятору больше информации для оптимизации и устраняет целый класс проблем, связанных с неожиданными исключениями.

Обратная сторона: цена перехода и ограничения Rust

Важно сказать не только о преимуществах, но и о реальных трудностях, с которыми сталкиваются команды при внедрении Rust.

Кривая обучения. Система владения — мощный инструмент, но она становится серьёзным барьером на старте. Данные опроса State of Rust Survey 2025 показывают, что 41,6% разработчиков считают Rust «слишком сложным», а 27,3% называют медленную компиляцию главной повседневной проблемой. Важно, что сложность неравномерна: новички борются с borrow checker, а опытные разработчики — со сложностью async и фрагментацией экосистемы асинхронного runtime.

Интеграция с существующим кодом. В реальности большинство организаций не переписывают всё с нуля, а внедряют Rust постепенно, бок о бок с C++. Именно здесь возникают нетривиальные проблемы: исследование ACM, в ходе которого было проанализировано 320 багов в инструментах bindgen, cbindgen и cxx, показало, что главное препятствие — не сбои или производительность, а неспособность генерировать корректный и функциональный код. Rust Foundation официально признаёт интероперабельность одной из главных инфраструктурных проблем и с 2024 года реализует специальную Interop Initiative для её решения.

Где экосистема Rust всё ещё отстаёт. Стоит добавить важную оговорку: C++ имеет 40-летнюю фору в виде огромного количества проверенных библиотек. В таких областях, как численные вычисления, графика, подключение к специализированным базам данных и AAA‑геймдев (например, Unreal Engine), Rust либо уступает, либо только начинает догонять. Для embedded‑разработки качество HAL‑крейтов (аппаратных абстракций) сильно варьируется от семейства микроконтроллеров к семейству, а поддержка со стороны вендоров остаётся неравномерной.

C++ не стоит на месте

Чтобы картина была честной, важно показать, что C++ тоже развивается. Комитет ISO завершил техническую работу над C++26, и ключевым направлением стало именно повышение безопасности: добавлена первая волна укрепления безопасности памяти и стандартизирована hardened standard library (проверки границ для контейнеров). Более амбициозная инициатива — «профили безопасности» (safety profiles), которые должны дать переносимые гарантии безопасности, — нацелена на C++29.

Сбалансированный взгляд на производительность

В чистых бенчмарках C++ иногда всё ещё выигрывает на несколько процентов, особенно в задачах, чувствительных к ручной настройке памяти или использованию Small String Optimization (SSO). Разрыв обычно невелик (в пределах 5–10%), но он существует. Главный вывод при этом остаётся прежним: разница в чистой скорости пренебрежимо мала на фоне выигрыша в безопасности и предсказуемости разработки.

Что можно сказать в заключение?

Rust станет языком по умолчанию для нового критического кода, но не заменит C++ полностью. Институциональный вектор уже задан: Microsoft официально поставила цель перевести миллионы строк кода с C и C++ на Rust к 2030 году, используя для этого ИИ‑агентов и новую инфраструктуру автоматической трансляции. Amazon, Google и Meta уже используют Rust не для экспериментов, а для гипервизоров, ядер ОС и браузерных движков, обслуживающих миллиарды пользователей. Если текущие темпы роста числа разработчиков сохранятся, по данным StackOverflow, Rust может обогнать C++ по абсолютному числу программистов примерно к 2030–2031 году, а по более консервативным оценкам JetBrains — к середине 2030-х. Однако важно понимать, что «обогнать по числу разработчиков» не означает «вытеснить из всех доменов»: в игровой индустрии (Unreal Engine, id Software) и встроенных системах на устаревших или экзотических платформах C++ сохранит сильные позиции гораздо дольше, поскольку там приоритет — не безопасность памяти, а совместимость с существующими фреймворками и проверенными вендорскими SDK.

C++ ответит на вызов, но его ответ будет запоздалым и частичным. Комитет ISO завершил техническую работу над C++26 в марте 2026 года, включив первую волну укрепления безопасности памяти, а амбициозные «профили безопасности» (profiles), которые должны дать переносимые гарантии, нацелены на C++29. Это означает, что даже при самом благоприятном сценарии инструменты, позволяющие писать на C++ с гарантиями, сопоставимыми с Rust, появятся в production‑компиляторах не раньше конца десятилетия, и то с оговорками. C++ останется незаменимым там, где критичны детерминированный контроль над памятью и временем выполнения — в высокочастотном трейдинге, HPC и задачах, чувствительных к ручной настройке аллокаций. Но в глазах регуляторов и корпораций, принимающих решения о новых проектах, C++ всё больше будет восприниматься как язык для поддержки и эволюции существующих систем, а не для создания критически важного нового кода.

Регуляторное давление превратится из рекомендаций в реальный фильтр для поставщиков. CISA уже запросила у производителей ПО планы перехода на безопасные языки для нового кода к 2026 году и планы миграции существующего кода к 2027 году, и хотя на данный момент это не имеет силы закона, формулировка «procurement implications» означает, что при государственных закупках отсутствие такой дорожной карты может стать flag‑ом для поставщика. К 2030 году этот механизм, вероятнее всего, станет более формализованным: для vendors, работающих с критической инфраструктурой, наличие публичной и выполняемой Memory Safe Roadmap будет де‑факто условием допуска к крупным контрактам. Это не запретит C++ полностью, но создаст мощный экономический стимул для новых проектов выбирать Rust или другой MSL, чтобы избежать будущих проблем с compliance.

Сам Rust продолжит закрывать свои слабые места. Rust Foundation в своей стратегии на 2026–2028 годы прямо называет приоритетами устойчивую инфраструктуру, поддержку мейнтейнеров, ответственный рост adoption и — что важно — коллаборацию с сообществом C++ по безопасной интероперабельности. Будущее — не в тотальной замене, а в сосуществовании. При этом важно трезво оценивать пределы безопасности Rust: он устраняет целый класс ошибок памяти, но не отменяет логические ошибки, целочисленные переполнения и проблемы в unsafe‑блоках, особенно при вызове ещё не переписанных C‑библиотек. Поэтому к 2030 году ключевым навыком станет не «знание Rust» или «знание C++» по отдельности, а способность проектировать границы между безопасным и небезопасным кодом и управлять ими.

Если эта публикация вас вдохновила и вы хотите поддержать автора — не стесняйтесь нажать на кнопку

View the original on Хабр →

KioskNews shows a cleaned-up reading view extracted from the publisher’s page — the original always lives on their site, not ours.