
Альтернативные примитивы чтения и записи, использующие функции Rtl* не по назначению.
Репозиторий со скриптами для демонстрации альтернативных примитивов чтения и записи с использованием функций Rtl* не по назначению.
RtlFillMemory принимает три аргумента: указатель на целевую область памяти, количество записываемых байт и одно значение-байт. Записывает только один байт в указанный блок памяти.
Примитив записи с использованием комбинации RtlInitializeBitMapEx и RtlFillMemory.
Сначала он перебирает строку блоками по 16 байт, разделяя каждый блок на два 8-байтовых значения. Первый 8-байтовый блок сохраняется в первый аргумент RtlInitializeBitMapEx, а второй 8-байтовый блок — во второй аргумент.
Затем, если остаётся дополнительный 8-байтовый блок, он записывается с помощью RtlInitializeBitMapEx с NULL в качестве второго параметра.
Наконец, если остаётся меньше 8 байт, они записываются по одному байту с помощью RtlFillMemory, пока вся строка не будет скопирована в целевой буфер.
Примитив чтения с использованием RtlQueryDepthSList. Полезен для поиска ROP-гаджетов, сравнения байт, обнаружения хуков и т. д. Здесь я демонстрирую простую инъекцию процесса с помощью ROP-гаджета. RtlQueryDepthSList принимает единственный аргумент — адрес памяти, из которого нужно читать, но читает только 2 байта и возвращает 4-байтовое значение.