В предыдущей статье я рассказывал про фреймворки для обхода антивируса и EDR. Сегодня рассмотрим метод обхода антивируса, который называется API Hashing — техника, которую разработчики вредоносного ПО применяют, чтобы скрыть подозрительные вызовы Windows API от таблицы импорта адресов портативного исполняемого файла (PE). Это затрудняет анализ, поскольку становится сложнее определить, какие функции вызываются.
Еще по теме: Обход антивируса с помощью Haskell
Как работает API Hashing
Проблема для разработчиков вредоносного ПО: если есть PE с неповрежденной IAT (Import Address Table), легко понять, каковы возможности PE. Например, если видно, что двоичный файл загружает Ws2_32.dll, можно предположить, что он имеет сетевые возможности.
Чтобы усложнить первоначальный анализ PE, вирусописатели скрывают подозрительные вызовы API от IAT с помощью API-хеширования. Таким образом, когда аналитик запустит вредоносный двоичный файл через утилиту strings или откроет его в PE-парсере, подозрительные Windows API будут скрыты.
Кстати, мы уже рассказывали о технике обхода антивирусов с помощью API Hashing.
Обход антивируса с помощью API Hashing
Предположим, у нас есть вредоносное ПО, которое использует функцию CreateThread. Если мы скомпилируем код и проанализируем его с помощью PE-парсера, увидим, что CreateThread — одна из импортированных функций. Однако если мы применим технику API Hashing, то CreateThread исчезнет из IAT.
Для этого разработчики вредоносного ПО могут использовать следующий подход:
- Создается хеш‑функция, которая принимает имя функции (например, CreateThread) и возвращает уникальное хеш‑значение.
- Вредоносное ПО во время выполнения перебирает все экспортированные функции из библиотеки (например, kernel32.dll), вычисляет их хеши и сравнивает с хешем CreateThread.
- Как только хеш совпадает, вредоносное ПО получает адрес функции и может вызвать ее напрямую, минуя IAT.
Рассмотрим подробнее. Как мы должны получить хеш от вызова API?
У нас есть пример алгоритма хеширования, который может преобразовать любую функцию в хеш:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
$APIsToHash = @("VirtualAlloc") $APIsToHash | % { $api = $_ $hash = 0x35 [int]$i = 0 $api.ToCharArray() | % { $l = $_ $c = [int64]$l $c = '0x{0:x}' -f $c $hash += $hash * 0xab10f29f + $c -band 0xffffff $hashHex = '0x{0:x}' -f $hash $i++ write-host "Iteration $i : $l : $c : $hashHex" } write-host "$api`t $('0x00{0:x}' -f $hash)" } |
За основу для хеширования мы взяли функцию VirtualAlloc. Она позволяет зарезервировать определенный объем памяти.
Преобразование функции в хеш:
Проблема только в том, что шелл Meterpreter делает вызов ко множеству API, включая ExitProcess, LoadLibraryA, VirtualAlloc и VirtualFree. И это далеко не полный список. Что же нам делать? Здесь помогает Randomise-api-hashes-cobalt-strike. Этот скрипт вычисляет хеши для огромного множества API и заменяет их названия в шелл‑коде. Давай установим его на Kali Linux и посмотрим, как он работает.
Клонируем репозиторий.
Генерируем шелл‑код в сыром виде и записываем в файл с расширением .bin.
И наконец, напустим инструмент на file.bin.
Заметил цифру 64 после названия скрипта? Это мы прописываем архитектуру. Разная разрядность — разные вызовы API. После отработки мы получаем файл file.bin_0xf9.bin. Если понадобится получить шелл‑код в сыром виде (С-code), то вновь используем xxd.
А что по обнаружениям?
VirusTotal дал 11 из 69.
И решения из списка исследуемых не дали отрицательный результат.
Этот шелл‑код уже можно скомпилировать в .exe.
Заключение
Мы рассмотрели интересный метод обхода антивирусов — API Hashing. Его важно учитывать сотрудникам компаний, отвечающих за защиту ресурсов и предотвращение реализации киберугроз.
Также рекоммедую посмоттеть другие продукты этой компаниии и излвечь выгоду которую можете поличить из этой статьи.
ПОЛЕЗНЫЕ ССЫЛКИ:
- Сокрытие вируса в архиве ZIP и RAR
- Как скрыть процессы от антивирусов
- Как обойти антивирус с помощью Chimera