Рандомизация расположения адресного пространства ( ASLR ) — это метод компьютерной безопасности , используемый для предотвращения эксплуатации уязвимостей повреждения памяти . [ 1] Чтобы не дать злоумышленнику надежно перенаправить выполнение кода, например, на определенную эксплуатируемую функцию в памяти, ASLR случайным образом упорядочивает позиции адресного пространства ключевых областей данных процесса , включая базу исполняемого файла и позиции стека , кучи и библиотек .
Проект Linux PaX впервые ввел термин «ASLR» и опубликовал первый дизайн и реализацию ASLR в июле 2001 года в качестве патча для ядра Linux. Он рассматривается как полная реализация, предоставляющая патч для рандомизации стека ядра с октября 2002 года. [2]
Первой популярной операционной системой, поддерживающей ASLR по умолчанию, стала OpenBSD версии 3.4 в 2003 году [3] [4], за которой в 2005 году последовал Linux.
Рандомизация адресного пространства препятствует некоторым типам атак безопасности, затрудняя для злоумышленника предсказание целевых адресов. Например, злоумышленники, пытающиеся выполнить атаки return-to-libc, должны найти код для выполнения, в то время как другие злоумышленники, пытающиеся выполнить shell-код, внедренный в стек, должны сначала найти стек. В обоих случаях система делает связанные адреса памяти непредсказуемыми с точки зрения злоумышленников. Эти значения должны быть угаданы, и ошибочная догадка обычно не может быть восстановлена из-за сбоя приложения.
Рандомизация макета адресного пространства основана на низкой вероятности того, что злоумышленник угадает местоположение случайно размещенных областей. Безопасность повышается за счет увеличения пространства поиска. Таким образом, рандомизация адресного пространства более эффективна, когда в случайных смещениях присутствует больше энтропии . Энтропия увеличивается либо за счет увеличения объема пространства виртуальной памяти , в течение которого происходит рандомизация, либо за счет сокращения периода, в течение которого происходит рандомизация. Период обычно реализуется как можно меньшим, поэтому большинство систем должны увеличивать рандомизацию пространства VMA.
Чтобы обойти рандомизацию, злоумышленники должны успешно угадать позиции всех областей, которые они хотят атаковать. Для областей данных, таких как стек и куча, куда может быть загружен пользовательский код или полезные данные, можно атаковать более одного состояния, используя слайды NOP для кода или повторяющиеся копии данных. Это позволяет атаке быть успешной, если область рандомизирована до одного из нескольких значений. Напротив, области кода, такие как база библиотеки и главный исполняемый файл, должны быть обнаружены точно. Часто эти области смешаны, например, кадры стека внедряются в стек, а библиотека возвращается в.
Могут быть объявлены следующие переменные:
mmap()
базы)mmap()
базовой энтропии)Чтобы рассчитать вероятность успеха злоумышленника, необходимо предположить количество попыток α, выполненных без прерывания сигнатурной IPS, правоохранительными органами или другими факторами; в случае грубой силы демон не может быть перезапущен. Количество соответствующих битов и сколько из них подвергается атаке при каждой попытке также должны быть рассчитаны, оставляя столько битов, которые злоумышленник должен победить.
Следующие формулы представляют вероятность успеха для заданного набора α попыток на N битах энтропии.
Во многих системах может быть в тысячах или миллионах. В 32-битных системах типичное количество энтропии N составляет 8 бит. [5] Для скоростей компьютеров 2004 года Шачам и его коллеги утверждают: «... 16 бит рандомизации адресов могут быть преодолены атакой методом подбора в течение нескольких минут». [6] (Утверждение авторов зависит от возможности атаковать одно и то же приложение несколько раз без какой-либо задержки. Правильные реализации ASLR, такие как включенные в grsecurity, предоставляют несколько методов, чтобы сделать такие атаки методом подбора невозможными. Один из методов заключается в предотвращении выполнения исполняемого файла в течение настраиваемого периода времени, если он давал сбой определенное количество раз.) В современных 64-битных системах эти числа обычно достигают как минимум миллионов. [ требуется цитата ][update]
Android, [7] [ необходим неосновной источник ] и, возможно, другие системы, [ которые? ] реализуют рандомизацию порядка загрузки библиотек , форму ASLR, которая рандомизирует порядок загрузки библиотек. Это обеспечивает очень малую энтропию. Приблизительное количество бит энтропии, предоставляемое для каждой необходимой библиотеки, показано ниже; это еще не учитывает различные размеры библиотек, поэтому фактическая полученная энтропия на самом деле несколько выше. Злоумышленникам обычно нужна только одна библиотека; математика становится более сложной с несколькими библиотеками и также показана ниже. Случай злоумышленника, использующего только одну библиотеку, является упрощением более сложной формулы для .
Эти значения, как правило, низкие даже для больших значений l , что наиболее важно, поскольку злоумышленники обычно могут использовать только стандартную библиотеку C , и поэтому часто можно предположить, что . Однако даже для небольшого числа библиотек здесь есть несколько бит энтропии, поэтому потенциально интересно объединить рандомизацию порядка загрузки библиотек с рандомизацией адресов VMA, чтобы получить несколько дополнительных бит энтропии. Эти дополнительные бит энтропии не будут применяться к другим сегментам mmap(), только к библиотекам.
Злоумышленники могут использовать несколько методов для уменьшения энтропии, присутствующей в рандомизированном адресном пространстве, от простых утечек информации до атаки на несколько бит энтропии за атаку (например, с помощью heap spraying ). С этим мало что можно сделать.
Возможна утечка информации о структуре памяти с использованием уязвимостей строки формата . Функции строки формата, такие как printf , используют переменный список аргументов для выполнения своей работы; спецификаторы формата описывают, как выглядит список аргументов. Из-за способа, которым аргументы обычно передаются, каждый спецификатор формата перемещается ближе к вершине кадра стека. В конечном итоге указатель возврата и указатель кадра стека могут быть извлечены, что позволяет узнать адрес уязвимой библиотеки и адрес известного кадра стека; это может устранить рандомизацию библиотеки и стека как препятствие для злоумышленника.
Также можно уменьшить энтропию в стеке или куче. Стек обычно должен быть выровнен по 16 байтам, и поэтому это наименьший возможный интервал рандомизации; в то время как куча должна быть выровнена по странице, обычно 4096 байт. При попытке атаки можно выровнять дублирующие атаки по этим интервалам; слайд NOP может использоваться с инъекцией шелл-кода, а строка ' /bin/sh
' может быть заменена на ' ////////bin/sh
' для произвольного количества слешей при попытке вернуться в систему . Количество удаленных битов точно для n атакованных интервалов.
Такие уменьшения ограничены из-за объема данных в стеке или куче. Стек, например, обычно ограничен8 МБ [8] и становится намного меньше; это позволяет максимум19 бит , хотя более консервативная оценка будет около 8–10 бит, соответствующих 4–16 КБ [8] заполнения стека. С другой стороны, куча ограничена поведением распределителя памяти; в случае glibc выделения свыше 128 КБ создаются с помощью mmap , ограничивая злоумышленников 5 битами сокращения. Это также является ограничивающим фактором при брутфорсе; хотя количество выполняемых атак может быть уменьшено, размер атак увеличивается достаточно, чтобы поведение могло в некоторых обстоятельствах стать очевидным для систем обнаружения вторжений .
Защищенные ASLR адреса могут быть украдены различными сторонними каналами, что исключает возможность смягчения. Недавние атаки использовали информацию, утекшую из буфера предиктора ветвления цели ЦП (BTB) или таблицы страниц блуждающего блока управления памятью (MMU). Неясно, можно ли смягчить этот класс атак ASLR. Если это невозможно, преимущество ASLR уменьшается или устраняется.
В августе 2024 года была опубликована статья [9] с эмпирическим анализом основных настольных платформ, включая Linux, macOS и Windows, путем изучения изменчивости размещения объектов памяти в различных процессах, потоках и перезапусках системы. Результаты показывают, что хотя некоторые системы по состоянию на 2024 год, такие как дистрибутивы Linux, обеспечивают надежную рандомизацию, другие, такие как Windows и macOS, часто не могут адекватно рандомизировать ключевые области, такие как исполняемый код и библиотеки. Более того, они обнаружили значительное снижение энтропии в энтропии библиотек после версии Linux 5.18 и определили пути корреляции, которые злоумышленник может использовать для значительного снижения сложности эксплуатации.
Несколько основных операционных систем общего назначения реализуют ASLR.
Android 4.0 Ice Cream Sandwich обеспечивает рандомизацию макета адресного пространства (ASLR) для защиты системных и сторонних приложений от эксплойтов из-за проблем с управлением памятью. Поддержка исполняемых файлов, не зависящих от позиции, была добавлена в Android 4.1. [10] Android 5.0 прекратил поддержку не-PIE и требует, чтобы все динамически связанные двоичные файлы были независимыми от позиции. [11] [12] Рандомизация порядка загрузки библиотек была принята в проект Android с открытым исходным кодом 26 октября 2015 года [7] [ необходим неосновной источник ] и была включена в выпуск Android 7.0.
В DragonFly BSD реализована реализация ASLR на основе модели OpenBSD, добавленная в 2010 году. [13] По умолчанию она отключена и может быть включена путем установки sysctl vm.randomize_mmap в значение 1.
Поддержка ASLR появилась в FreeBSD 13.0. [14] [15] Она включена по умолчанию с версии 13.2. [16]
Apple представила ASLR в iOS 4.3 (выпущенной в марте 2011 г.). [17]
KASLR был представлен в iOS 6. [18] Рандомизированная база ядра — это 0x01000000 + ((1+0xRR) * 0x00200000)
, где 0xRR
— случайный байт из SHA1 (случайные данные), сгенерированный iBoot (загрузчик iOS 2-го уровня). [19]
Ядро Linux по умолчанию включает слабую форму ASLR, начиная с версии ядра 2.6.12, выпущенной в июне 2005 года. [20] Патчи PaX и Exec Shield для ядра Linux предоставляют более полные реализации. Патч Exec Shield для Linux предоставляет 19 бит энтропии стека на период 16 байт и 8 бит рандомизации базы mmap на период 1 страницы из 4096 байт. Это помещает базу стека в область шириной 8 МБ, содержащую 524 288 возможных позиций, а базу mmap — в область шириной 1 МБ, содержащую 256 возможных позиций.
ASLR можно отключить для определенного процесса, изменив его область выполнения, используя personality(2)
. [21] Ряд опций sysctl управляет поведением основного ASLR. Например, kernel.randomize_va_space
управляет тем, что рандомизировать; самая сильная опция — 2. vm.mmap_rnd_bits
управляет количеством битов для рандомизации для mmap . [22]
Позиционно-независимый исполняемый файл (PIE) реализует случайный базовый адрес для основного исполняемого двоичного файла и действует с 18 апреля 2004 года. Он обеспечивает ту же случайность адреса для основного исполняемого файла, что и для общих библиотек. Функция PIE не может использоваться вместе с функцией предварительной компоновки для одного и того же исполняемого файла. Инструмент предварительной компоновки реализует рандомизацию во время предварительной компоновки, а не во время выполнения, поскольку по своей конструкции prelink нацелен на обработку перемещения библиотек до того, как это должен сделать динамический компоновщик, что позволяет выполнять перемещение один раз для многих запусков программы. В результате реальная рандомизация адресного пространства сведет на нет цель предварительной компоновки.
В 2014 году Марко-Гисберт и Риполл раскрыли технику offset2lib , которая ослабляет Linux ASLR для исполняемых файлов PIE. Ядра Linux загружают исполняемые файлы PIE сразу после своих библиотек; в результате между исполняемым файлом и библиотечными функциями существует фиксированное смещение. Если злоумышленник находит способ найти адрес функции в исполняемом файле, адреса библиотек также известны. Они продемонстрировали атаку, которая находит адрес менее чем за 400 попыток. Они предложили новую randomize_va_space=3
опцию для рандомизации размещения исполняемого файла относительно библиотеки, [5], но она еще не включена в апстрим по состоянию на 2024 год. [23]
Ядро Linux 5.18, выпущенное в мае 2022 года, снизило эффективность как 32-разрядных, так и 64-разрядных реализаций. Файловые системы Linux вызывают для ответа на mmapthp_get_unmapped_area
с файловой поддержкой . С изменением в 5.18 файлы размером более 2 МиБ возвращают выровненные по 2 МиБ адреса, поэтому их потенциально можно поддерживать огромными страницами . (Раньше повышенное выравнивание применялось только к отображениям Direct Access (DAX).) Тем временем библиотека C (libc) со временем выросла в размере и превысила этот порог в 2 МиБ, поэтому вместо того, чтобы быть выровненными по (обычно) границе страницы в 4 КиБ, как раньше, эти библиотеки теперь выровнены по 2 МиБ: потеря 9 бит энтропии. Для 32-разрядного Linux многие дистрибутивы вообще не показывают рандомизации в размещении libc. Для 64-разрядного Linux 28 бит энтропии сокращаются до 19 бит. В ответ Ubuntu увеличила свои настройки. [24] Мартин Дуча добавил тестовый пример Linux Test Project для обнаружения этой проблемы. [25]mmap_rnd_bits
Рандомизация адресного пространства ядра (KASLR) обеспечивает рандомизацию адресного пространства для образа ядра Linux путем рандомизации размещения кода ядра во время загрузки. [26] KASLR был объединен с основной веткой ядра Linux в версии ядра 3.14, выпущенной 30 марта 2014 года. [27] При компиляции его можно отключить во время загрузки, указав nokaslr в качестве одного из параметров загрузки ядра. [28]
В процессорах x86 существует несколько атак по сторонним каналам , которые могут привести к утечке адресов ядра. [29] [30] В конце 2017 года была разработана изоляция таблицы страниц ядра (KPTI, также известная как KAISER) для отражения этих атак. [31] [32] Однако этот метод не может защитить от атак по сторонним каналам, использующих коллизии в структурах прогнозирования ветвлений . [33]
С 2021 года [update]более мелкозернистая рандомизация макета адресного пространства ядра (или функциональная гранулярная KASLR, FGKASLR) является запланированным расширением KASLR для рандомизации вплоть до уровня функций. [34]
В Windows Vista (выпущенной в январе 2007 г.) и более поздних версиях от Microsoft ASLR включен только для исполняемых файлов и динамически подключаемых библиотек , которые специально связаны с поддержкой ASLR. [35] Для совместимости он не включен по умолчанию для других приложений. Обычно несовместимо только старое программное обеспечение, и ASLR можно полностью включить, отредактировав запись в реестре HKLM\SYSTEM\CurrentControlSet\Control\Session Manager\Memory Management\MoveImages
, [36] или установив Microsoft Enhanced Mitigation Experience Toolkit .
Расположение кучи , стека , блока среды процесса и блока среды потока также рандомизировано. В документе по безопасности от Symantec отмечено, что ASLR в 32-разрядной Windows Vista может быть не таким надежным, как ожидалось, и Microsoft признала слабость в его реализации. [37]
Системы предотвращения вторжений на основе хоста, такие как WehnTrust [38] и Ozone [39], также предлагают ASLR для операционных систем Windows XP и Windows Server 2003. WehnTrust имеет открытый исходный код. [40] Полные сведения о реализации Ozone недоступны. [41]
В феврале 2012 года [42] было отмечено , что ASLR на 32-битных системах Windows до Windows 8 может иметь сниженную эффективность в ситуациях с нехваткой памяти. Похожий эффект был достигнут и на Linux в том же исследовании. Тестовый код вызвал панику ядра в системе Mac OS X 10.7.3 , поэтому поведение ASLR в этом сценарии осталось неясным.
Поддержка ASLR в пользовательском пространстве появилась в NetBSD 5.0 (выпущена в апреле 2009 г.) [43] и была включена по умолчанию в NetBSD-current в апреле 2016 г. [44]
Поддержка ядра ASLR на amd64 была добавлена в NetBSD-current в октябре 2017 года, что сделало NetBSD первой системой BSD, поддерживающей KASLR. [45]
В 2003 году OpenBSD стала первой основной операционной системой, которая поддерживала сильную форму ASLR и активировала ее по умолчанию. [3]
OpenBSD завершила поддержку ASLR в 2008 году, когда добавила поддержку двоичных файлов PIE . [46] Функция malloc(3) OpenBSD 4.4 была разработана для повышения безопасности за счет использования возможностей ASLR и gap page, реализованных как часть mmap
системного вызова OpenBSD , а также для обнаружения ошибок использования после освобождения. [47] Выпущенная в 2013 году, OpenBSD 5.3 стала первой основной операционной системой, которая по умолчанию включила позиционно-независимые исполняемые файлы на нескольких аппаратных платформах , а OpenBSD 5.7 активировала позиционно-независимые статические двоичные файлы (Static-PIE) по умолчанию. [46]
В Mac OS X Leopard 10.5 (выпущенной в октябре 2007 года) Apple представила рандомизацию для системных библиотек. [48]
В Mac OS X Lion 10.7 (выпущенной в июле 2011 года) Apple расширила свою реализацию, чтобы охватить все приложения, заявив, что «рандомизация адресного пространства (ASLR) была улучшена для всех приложений. Теперь она доступна для 32-битных приложений (как и защита динамической памяти), что делает 64-битные и 32-битные приложения более устойчивыми к атакам». [49]
Начиная с OS X Mountain Lion 10.8 (выпущенной в июле 2012 года) и более поздних версий, вся система, включая ядро, а также kexts и зоны, случайным образом перемещается во время загрузки системы. [50]
ASLR был представлен в Solaris, начиная с Solaris 11.1 (выпущен в октябре 2012 г.). ASLR в Solaris 11.1 может быть установлен для всей системы, для каждой зоны или для каждого двоичного файла. [51]
Было продемонстрировано, что атака по сторонним каналам с использованием целевого буфера ветвления позволяет обойти защиту ASLR. [33] В 2017 году была продемонстрирована атака под названием «ASLR⊕Cache», которая могла обойти ASLR в веб-браузере с помощью JavaScript. [52]