На проверке Cross-VM Rowhammer атака: как переворот битов в DRAM ломает изоляцию арендаторов в облаке

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


В 2016 году ребята из Ohio State University (Xiao, Zhang, Zhang, Teodorescu) показали на USENIX Security штуку, от которой у облачных провайдеров дёрнулся глаз: вредоносная виртуальная машина на гипервизоре Xen переворачивает биты в DRAM и получает доступ к произвольной физической памяти хоста - включая память соседних арендаторов. Работу процитировали 398 раз, а облачные провайдеры тихо начали отключать ряд оптимизаций памяти. Годом позже команда Stormshield воспроизвела аналогичный сценарий на KVM: с атакующей VM удалось подменить результат аутентификации в libpam на соседней VM и войти без пароля. Cross-VM rowhammer атака - редкий случай, когда физический дефект кремния превращается в полноценный вектор пробития изоляции между арендаторами облака. Никакой патч ядра тут не поможет - проблема в физике конденсаторов.

Зачем атакующему переворачивать биты в соседней VM​

Мультитенантное облако строится на обещании: данные арендатора изолированы от соседей по физическому серверу. Гипервизор (KVM, Xen, Hyper-V) реализует эту изоляцию через виртуализацию памяти - каждая VM видит своё «физическое» адресное пространство, но реально делит DRAM-модули с другими арендаторами. Rowhammer атака на облако ломает это обещание на аппаратном уровне, ниже гипервизора. Тут уже не важно, насколько хорошо настроены группы безопасности.

Атакующий, арендовавший VM на том же физическом хосте, что и жертва, способен:
  • Модифицировать PTE (Page Table Entries) жертвы - получить произвольное чтение и запись в её физическую память
  • Подменить результат аутентификации - перевернув бит в состоянии pam_unix.so, войти в соседнюю VM без пароля (продемонстрировано Stormshield на KVM)
  • Извлечь криптографические ключи - атака RAMBleed, связанная с CVE-2019-0174, позволяет читать данные из соседних ячеек DRAM. Согласно NVD, уязвимость затрагивает ряд процессоров Intel (i9-9900X, i9-9920X, i9-9960X и др.)
  • Обойти sudo - атака Phoenix (ETH Zurich, 2025) продемонстрировала эскалацию привилегий через переворот бита в проверке sudo на DDR5
По данным CrowdStrike Global Threat Report 2025, количество cloud intrusion инцидентов выросло на 26% год к году. Rowhammer - не массовый вектор, но один из немногих, работающих ниже уровня гипервизора.

Место в kill chain: аренда VM на целевом хосте (Initial Access) → профилирование физической памяти (Discovery) → переворот битов в структурах данных жертвы (Lateral Movement / Privilege Escalation).

[Применимо: мультитенантные облачные среды с shared hosts на KVM, Xen. Не применимо: dedicated hosts, bare-metal instances, среды с аппаратной изоляцией памяти.]

Физика DRAM: почему переворот битов в памяти DRAM вообще возможен​

Каждая ячейка DRAM - конденсатор и транзистор доступа. Бит хранится как заряд конденсатора. Ячейки организованы в строки (rows) и столбцы (columns) внутри банков (banks). Команда ACTIVATE открывает строку, считывая заряд в row buffer, после чего он восстанавливается. Весь DRAM рефрешится с фиксированным интервалом - 64 мс для DDR4.

Проблема в том, что при многократной активации одной строки (aggressor row) заряд утекает из соседних строк (victim rows). Три гипотезы объясняют этот эффект (по обзору в PMC, 2024):
  1. Электрический мост - проводящие каналы формируются между конденсаторами соседних строк при уплотнении техпроцесса
  2. Электромагнитная связь - переключение word-line индуцирует наводки на соседнем word-line через ёмкостную связь
  3. Инжекция горячих носителей - длительное переключение word-line вызывает hot-carrier injection в подложку и смежные строки
Результат: если victim-ячейка не успевает дождаться планового refresh, заряд уходит ниже порога - происходит bit flipping DRAM. Из 0 в 1 или наоборот. Это не программный баг - это row hammer уязвимость DRAM, физическое свойство плотно упакованных конденсаторов в нанометровых техпроцессах. Производители памяти знают об этом с 2014 года, и пока ни одно поколение DRAM не решило проблему окончательно.

Полная цепочка cross-VM Rowhammer атаки​

Co-location и маппинг физических адресов​

Первое предусловие - co-location attack VM: оказаться на одном физическом хосте с жертвой. В публичных облаках это решается статистически - атакующий арендует пачку VM в одном регионе и availability zone, пока одна из них не окажется co-located с целевой VM. Xiao et al. отмечают, что атаки «applicable in modern public clouds where Xen paravirtualization technology is adopted». Звучит как лотерея, но при достаточном бюджете на VM - лотерея с предсказуемым исходом.

Второе предусловие - определить маппинг виртуальных адресов на физические адреса DRAM (channel, rank, bank, row, column). Из гостевой VM прямого доступа к физической адресации хоста нет, но есть обходные пути.

Transparent Huge Pages (THP) - механизм ядра Linux, при котором фоновый поток khugepaged объединяет обычные 4 КБ-страницы в huge pages по 2 МБ. Huge page - 2 МБ непрерывной физической памяти. Как показано в исследовании Stormshield, одна huge page покрывает несколько строк DRAM. Для Intel Sandy Bridge (биты 18-33 отвечают за выбор строки) huge page на 2 МБ захватывает ровно 8 строк. Этого достаточно для double-sided hammering внутри одной huge page.

Маппинг физических адресов для Sandy Bridge (по данным Mark Seaborn, цитируется Stormshield):
  • Биты 0-5: смещение внутри строки (нижние 6 бит)
  • Бит 6: выбор канала
  • Биты 7-13: старшие 7 бит смещения внутри строки
  • Биты 14-16: выбор банка с XOR-схемой (((addr >> 14) & 7) ^ ((addr >> 18) & 7))
  • Бит 17: выбор rank
  • Биты 18-33: выбор строки
Атакующий из своей VM выделяет большой буфер, выровненный по границе 2 МБ, проверяет через /proc/self/pagemap наличие huge page backing и использует известный маппинг для навигации по строкам DRAM.

[Предусловия: Linux-хост с включённым THP (по умолчанию в большинстве дистрибутивов). На ARM-архитектурах и нестандартных контроллерах памяти маппинг отличается - требуется реверс-инжиниринг.]

Double-sided hammering через Transparent Huge Pages​

Double-sided hammering - обращение к строкам k-1 и k+1 для провоцирования бит-флипа в целевой строке k. Эффективнее single-sided в разы: victim row получает утечку заряда с двух сторон одновременно.

Из гостевой VM атакующий перебирает каждый 2 МБ-блок, проверяет huge page backing и для каждой пары строк-агрессоров (r, r+2) молотит пары адресов с учётом XOR-схемы банков. Без инструкции clflush ничего не выйдет - она вытесняет кешлайн из всех уровней кеша CPU. Без неё повторные чтения обслуживаются из кеша и строка DRAM не активируется.
C:
// Double-sided hammering - адаптировано из исследования Stormshield (2017)
void hammer(volatile char *row_a, volatile char *row_b, int iterations) {
    for (int i = 0; i < iterations; i++) {
        *row_a;                                    // чтение строки r
        *row_b;                                    // чтение строки r+2
        asm volatile("clflush (%0)" :: "r"(row_a)); // сброс кеша
        asm volatile("clflush (%0)" :: "r"(row_b));
    }
}
Ключевое наблюдение из Stormshield: бит-флипы воспроизводимы. Некоторые ячейки памяти хуже изолированы физически - если ячейка перевернулась один раз, с высокой вероятностью перевернётся снова при повторном hammering. Это позволяет составить карту уязвимых ячеек до начала эксплуатации памяти в мультитенантном облаке. По сути, у DRAM-модуля есть свой «отпечаток пальца» из слабых ячеек.

Flip Feng Shui: эксплуатация memory deduplication​

Hammering даёт бит-флипы, но как контролировать, что именно переворачивается? Атакующий не выбирает, куда гипервизор разместит данные жертвы в физической памяти. Здесь в игру вступает memory deduplication attack через KSM.

KSM (Kernel Same-page Merging) - механизм ядра Linux, периодически сканирующий анонимные страницы памяти с флагом MADV_MERGEABLE и объединяющий идентичные страницы в одну copy-on-write копию. В мультитенантной среде KSM экономит гигабайты RAM: если две VM запускают одинаковый nginx, их идентичные страницы кода сливаются в одну физическую копию. Для облачного оператора - экономия. Для атакующего - side-channel атака в облаке, позволяющая контролировать расположение данных жертвы в физической памяти. Красивая оптимизация, которая оборачивается вектором атаки.

Техника flip feng shui (Razavi et al.) эксплуатирует KSM для хирургического размещения данных жертвы в уязвимую ячейку DRAM:
  1. Профилирование. Атакующий молотит память из своей VM и составляет карту уязвимых ячеек: адрес → направление флипа (0→1 или 1→0)
  2. Подготовка. Атакующий загружает в свою память контент, идентичный целевым данным жертвы (например, authorized_keys или код pam_unix.so). Страница размещается в huge page с известной уязвимой ячейкой
  3. KSM объединяет страницы. Обе страницы идентичны - KSM сливает их в одну физическую копию, которая теперь лежит в строке с уязвимой ячейкой
  4. Повторный hammering. Атакующий молотит строки-агрессоры. Бит переворачивается в объединённой странице, видимой обеим VM
  5. Результат. Жертва читает модифицированные данные из своей памяти. Ни одного алерта.
По данным Stormshield, Razavi et al. ослабляли RSA-модуль в файле authorized_keys жертвы - после переворота бита модуль становился факторизуемым, атакующий вычислял соответствующий приватный ключ и аутентифицировался по SSH на соседней VM.

Stormshield пошли другим путём: вместо файлов они корраптили состояние запущенного процесса - модуль pam_unix.so в libpam. Переворот бита в коде проверки аутентификации (или в возвращаемом значении) давал успешную аутентификацию без валидного пароля. Атака на соседний арендатор VM реализована полностью из user-space гостевой VM. Без эксплойтов ядра, без побега из контейнера - чистая физика.

Тонкость взаимодействия THP и KSM: THP собирает 4 КБ-страницы в 2 МБ huge pages, а KSM наоборот разбивает huge pages при обнаружении одинаковых 4 КБ-блоков. Решение из Stormshield: заполнять верхние 8 байт каждой 4 КБ-страницы уникальными случайными данными. KSM не объединяет страницы, различающиеся хотя бы в одном байте, - а атакующий сохраняет контроль над тем, какие именно страницы подлежат объединению.

Практический разбор: от бит-флипа к shell на чужой VM​

Требования к окружению​

  • Гипервизор: KVM или Xen (паравиртуализация). Xiao et al. демонстрировали на Xen PV, Stormshield - на KVM. На VMware vSphere и Hyper-V практических PoC в открытых источниках нет
  • Хост: Linux с включённым KSM (/sys/kernel/mm/ksm/run = 1) и THP (/sys/kernel/mm/transparent_hugepage/enabled = always)
  • DRAM: DDR3 наиболее уязвим (нет TRR). DDR4 с TRR - частично защищён, но TRR обходится атакой Blacksmith (2021). DDR5 - обходится атакой Phoenix (ETH Zurich, 2025)
  • CPU: Intel Sandy Bridge и новее - маппинг физических адресов документирован. Для AMD Zen требуется дополнительный реверс-инжиниринг
  • RAM атакующей VM: минимум 4 ГБ для эффективного профилирования уязвимых ячеек
  • ECC: серверная ECC-память корректирует одиночные бит-флипы, усложняя атаку. По данным Kaspersky, ECC «не делает атаку полностью невозможной»
Цепочка действий:

Шаг 1. Профилирование. Выделяем буфер, покрывающий максимум доступной физической памяти. Для каждого 2 МБ-блока проверяем huge page backing:
C:
// Проверка huge page backing - пример для демонстрации концепции
int fd = open("/proc/self/pagemap", O_RDONLY);
uint64_t entry;
pread(fd, &entry, sizeof(entry), (vaddr / 4096) * 8);
int is_huge = (entry >> 22) & 1;
Для каждого подтверждённого huge page перебираются пары строк-агрессоров с вариацией битов канала и rank. Hammering - около 1 000 000 итераций на пару. После hammering проверяется, изменились ли данные в victim-строке.

Шаг 2. Карта бит-флипов. Результат: таблица {offset_в_huge_page → направление_флипа}. На DDR3 без TRR один проход по 8 ГБ обнаруживает сотни уязвимых ячеек. На DDR4 с TRR - существенно меньше, но паттерны Blacksmith увеличивают число обнаруженных ячеек.

Шаг 3. Подготовка страницы-приманки. Выделяем 4 КБ-страницу с контентом, идентичным целевым данным жертвы. Критический момент - правильный offset: бит-флип должен попасть в конкретный байт целевой структуры (PTE, RSA-модуль, код проверки пароля).

Шаг 4. Ожидание слияния KSM. Интервал настраивается в /sys/kernel/mm/ksm/sleep_millisecs. Атакующий ждёт, пока KSM обнаружит идентичные страницы и объединит их в одну физическую копию. Тут нужно терпение - в зависимости от настроек это может занять от секунд до минут.

Шаг 5. Повторный hammering. После слияния снова молотим строки-агрессоры. Бит-флип происходит в объединённой странице. Для PTE-атаки это даёт произвольный доступ к физической памяти хоста. Для атаки на libpam - аутентификацию без пароля.

[Когда техника НЕ работает: KSM отключён на хосте; ECC корректирует все одиночные бит-флипы; гипервизор использует SLAT/EPT с дополнительной рандомизацией; DRAM с актуальным Fine Granularity Refresh; VM работает в режиме HVM/PVH вместо Xen PV.]

Защита от Rowhammer в облачной инфраструктуре​

Phoenix (ETH Zurich, 2025) показал неприятную вещь: rowhammer виртуализация-атаки работают против всех 15 протестированных модулей DDR5 от SK hynix. Исследователи обнаружили, что после 128 отслеживаемых TRR обращений возникает окно из 64 обращений с ослабленной защитой. Второе окно - после 2608 интервалов обновления. Атака на PTE (произвольное чтение/запись) сработала на всех модулях за время от 5 секунд до 7 минут. Проблема не решена даже в актуальном поколении DRAM.

МеханизмЧто делаетОграниченияКогда использоватьКогда НЕ использовать
Отключение KSMУбирает вектор deduplicationРост потребления RAM на 15-30%Продакшн с чувствительными даннымиDev/test среды с ограниченной памятью
ECC MemoryКорректирует одиночные бит-флипыНе исключает атаку полностью (по данным Kaspersky)Всегда в серверных средахНе полагаться как на единственную защиту
TRR (DDR4/DDR5)Аппаратный рефреш victim-строкОбходится Blacksmith (DDR4), Phoenix (DDR5)Стандарт в modern DRAMНе надёжен как единственная защита
Отключение THPЛишает атакующего непрерывной памятиДеградация производительности VMSecurity-critical хостыWorkloads с интенсивной работой с памятью
Dedicated hostsФизическая изоляция арендаторовСтоимость x2-x5 vs sharedФинансы, здравоохранение, гостайнаБюджетные проекты
Fine Granularity RefreshИзменяет схему рефреша на стороне контроллераДоступен только на новых платформахНовые поколения CPULegacy-оборудование
SLAT/EPTАппаратная изоляция page tables гостяНе защищает от bit flips в user-space данныхСовременные гипервизорыXen PV без nested paging

Исследователи из ETH Zurich предложили два подхода: уменьшить интервал рефреша всех ячеек (ценой повышенного энергопотребления и нагрева) и перейти на публично верифицируемые алгоритмы защиты вместо проприетарных TRR-реализаций - по аналогии с принципами проектирования криптосистем. Второй пункт особенно показателен: security through obscurity в кремнии работает не лучше, чем в софте.

Чеклист для облачных операторов​

📚 Часть контента скрыта. Этот материал доступен участникам сообщества с рангом One Level или выше
Получить доступ просто — достаточно зарегистрироваться и проявить активность на форуме

Три года я собирал лабораторные стенды с DIMM-модулями разных поколений и измерял частоту рефреша для обхода TRR-защиты. Вот что стало очевидно: производители памяти проигрывают эту гонку. Каждое новое поколение TRR обходится исследователями за 1-2 года после выхода - Blacksmith сломал DDR4, Phoenix сломал DDR5.

Крупные облачные провайдеры решили проблему не на уровне кремния, а административно: отключили KSM и предлагают dedicated hosts за дополнительную плату. Для AWS, GCP и Azure cross-VM rowhammer стал вопросом ценовой сегментации: хочешь изоляцию - плати за dedicated.

Но частные облака на OpenStack, Proxmox, самосборном KVM - другая история. Там KSM часто включён по умолчанию, ECC экономят, а dedicated hosts - непозволительная роскошь. Именно эти инфраструктуры остаются наиболее уязвимыми к эксплуатации памяти в мультитенантном облаке. Парадокс: у кого меньше всего ресурсов на защиту, у того наибольшая поверхность атаки.

Пока производители DRAM полагаются на проприетарные TRR-алгоритмы вместо публично верифицируемых схем, каждое новое поколение памяти будет порождать новый Rowhammer-bypass в течение пары лет после выхода. Защита от rowhammer в облачной инфраструктуре - не вопрос одного патча, а набор организационных и аппаратных мер. Начните с echo 0 > /sys/kernel/mm/ksm/run на продакшн-хостах - прямо сейчас проверьте, что там стоит.
 
Мы в соцсетях:

Взломай свой первый сервер и прокачай скилл — Начни игру на HackerLab

Похожие темы

🚀 Первый раз на Codeby?
Гайд для новичков: что делать в первые 15 минут, ключевые разделы, правила
Начать здесь →
🧭 Навигатор · ИБ 2026
Не знаешь, какой трек твой?
5 направлений ИБ, реальные зарплаты и точка входа для каждого — в одном треде.
JuniorSenior+
100K → 600K+ ₽ /мес
Открыть навигатор →
🔴 Свежие CVE, 0-day и инциденты
То, о чём ChatGPT ещё не знает — обсуждаем в реальном времени
Threat Intel →
💼 Вакансии и заказы в ИБ
Pentest, SOC, DevSecOps, bug bounty — работа и проекты от проверенных компаний
Карьера в ИБ →

HackerLab