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

Корень проблемы

Изначально в блоге Google Project Zero сообщалось об успешной реализации трех вариантов атаки на кеш процессора:

  • злонамеренная загрузка данных в кеш;
  • обход границ массива;
  • инъекция целевой ветви.

Формально их описали как две сходные уязвимости — Meltdown (первый вариант атаки) и Spectre (второй и третий варианты). Сценарии их практического использования зависят от микроархитектуры ЦП и операционной системы, в разной степени затрагивая производителей железа, облачных провайдеров и сообщество Linux.

Авторы исследования знали о проблеме давно. 1 июня 2017 года они отправили свои отчеты в Intel, AMD и ARM, пообещав не публиковать детали до тех пор, пока разработчики не выпустят патчи. Однако произошла утечка информации, из-за которой им пришлось обнародовать подробности раньше.

Уязвимости имеют много сходных черт на концептуальном уровне. Обе делают возможным проведение атаки по стороннему каналу, используя недостатки физической реализации процессоров. Впервые данный класс атак подробно описал Пол Кёхер (Paul Köcher) еще в 1996 году применительно к популярным криптосистемам. Он также выступил соавтором исследования Meltdown и Spectre.

На сегодня продемонстрировано три базовых сценария использования этих уязвимостей, которые мы подробнее разберем ниже. Важно то, что во всех вариантах конечной целью атак является кеш. Разными уловками процессор вынуждают кешировать значение байта из адреса памяти, недоступного вредоносному процессу.

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

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

 

Бомба замедленного действия

Сама идея внеочередного исполнения инструкций была предложена IBM в 1963 году. Рядовые пользователи столкнулись с ней только в 1995 году, когда появился первый Pentium Pro. С тех пор линейный конвейер канул в Лету, а все современные процессоры используют архитектуру с внеочередным (out-of-order) и одновременно упреждающим (или спекулятивным — speculative) механизмом исполнения команд.

Как же это работает? Для программиста все выглядит просто. Он отправил очередь инструкций на вход и получил ее исполнение на выходе. Однако внутри процессора творится своя магия. Современное процессорное ядро использует многоуровневый конвейер с нелинейными путями. Все входящие инструкции в нем кешируются и декодируются по нескольку штук за такт. Они дробятся на микрооперации, которые переупорядочиваются в собственном буфере (ROB, Re-Order Buffer). Ни одна из них не работает с реальными адресами памяти и физическими регистрами процессора. Блок управления памятью транслирует виртуальные адреса и определяет параметры доступа к ним.

После ROB микрооперации отправляются в станцию резервации, где обрабатываются параллельно на разных исполнительных блоках. Вдобавок современные процессоры используют разные типы кешей для ускорения обработки данных, изначально загружаемых в не слишком быструю оперативную память. Простейший кеш для инструкций применялся еще в 1982 году, а кеш данных используется с 1985 года. Сейчас они оба относятся к базовому кешу первого уровня (L1), помимо которого появились L2 и L3 общего назначения.

Блоковая диаграмма конвейера Intel Skylake / Kaby Lake (источник: wikichip.org)
Блоковая диаграмма конвейера Intel Skylake / Kaby Lake (источник: wikichip.org)

Все эти архитектурные навороты создавались для уменьшения времени простоя отдельных исполнительных блоков процессора. Пока один блок ожидает загрузки данных из оперативной памяти для своей инструкции, другой параллельно обрабатывает следующие. В этом ему помогает MMU (Memory Management Unit) и общая архитектура конвейера, который старается работать на упреждение и постоянно подгружает наиболее востребованные данные в кеш.

Ключевой момент в этой схеме состоит в том, что в большинстве процессоров все проверки легитимности исполнения инструкций и даже контроль за разделением доступа к памяти в самом MMU происходят уже на заключительном этапе обработки инструкций, когда начинается выстраивание промежуточных результатов в порядке исходной очереди команд. Запрещенные операции игнорируются (вызывают исключение), а невостребованные данные при этом остаются в кеше. Собственно, это и есть главная проблема.

В большей мере задержками в проверке условий и длинным забеганием вперед по ветвям инструкций грешат процессоры Intel с длинным конвейером (кроме Itanium и первых Atom), но AMD и даже ARM это тоже касается — просто в эксплоитах для них потребуется более точный таймер, другие размеры массивов и техники забивания кеша. Если Meltdown для них пока не смогли убедительно воспроизвести, то Spectre — вполне.

Блоковая диаграмма конвейера AMD Zen (источник: wikichip.org)
Блоковая диаграмма конвейера AMD Zen (источник: wikichip.org)

Целых 27 лет ведущие разработчики считали, что скорость обработки инструкций важнее безопасности, а все проверки можно делать уже после пробного исполнения команд «на выходе» из конвейера. В том или ином виде внеочередное исполнение сегодня реализовано во всех процессорах. Из-за параллельной работы исполнительных блоков задержка в обработке исключения, лаг MMU и очистки кеша тоже есть всегда, просто в случае микроархитектуры Core они заметнее и ими проще воспользоваться.

Продолжение доступно только подписчикам

Вариант 1. Оформи подписку на «Хакер», чтобы читать все материалы на сайте

Подписка позволит тебе в течение указанного срока читать ВСЕ платные материалы сайта. Мы принимаем оплату банковскими картами, электронными деньгами и переводами со счетов мобильных операторов. Подробнее о подписке

Вариант 2. Купи один материал

Заинтересовала информация, но нет возможности оплатить подписку? Тогда этот вариант для тебя! Обрати внимание: этот способ покупки доступен только для материалов, опубликованных более двух месяцев назад.


7 комментариев

  1. joker2k1

    11.01.2018 at 17:03

    игровые серверы то зачем патчить? там сторонний код чтоли выполняется?

  2. Ckomop0x

    11.01.2018 at 17:35

    Спасибо за очень детальную статью!

  3. Mr-r00t

    12.01.2018 at 11:09

    Спасибо, именно из за таких статей сохраняю подписку.

  4. nm0t

    16.01.2018 at 00:54

    Спасибо за статью, максимально подробное и доходчивое объяснение на русском языке, из всех статей по данной теме (полдня пытался разобраться, надо было сразу здесь читать)

  5. robotobor

    16.01.2018 at 09:49

    Спасибо, на высоте, как всегда.

  6. Str4n1x

    25.02.2018 at 02:07

    Спасибо за подробное объяснение. Только проблема оказывается не во внеочередном исполнении команд, а в том, что процессор не чистит кэш при ошибках предсказания.

Оставить мнение

Check Also

Устройства на iOS можно скомпрометировать из-за бага в механизме синхронизации через Wi-Fi

На конференции RSA 2018 специалисты Symantec рассказали об опасной проблеме в механизме си…