Skip to content
KitploitKITPLOIT
ИнструментыЭксплойтыБлог
Log in
Отправить
ИнструментыЭксплойтыБлог
Отправить

Инструменты для хакинга, пентеста и кибербезопасности — ваш арсенал защиты!

Kitploit — это каталог инструментов для хакинга, кибербезопасности и пентестинга. Находите последние обновления проектов для поиска уязвимостей, анализа систем, автоматизации тестирования и усиления вашей безопасности.

··Ленты·Контакты·Конфиденциальность·© 2026 Kitploit

Каталог инструментов

Категории

Все категории
Loading categories
px-vm — Набор инструментов для обратного проектирования виртуальной машины байт-кода PerimeterX, включающий дизассемблер на основе CFG, 5-уровневый конвейер дешифрования, восстановление таблицы опкодов и очиститель эмуляции стека для исследований в области безопасности, связанных с fingerprinting обнаружения ботов. | Kitploit
Инструменты/GitHubGitHub/b9ph0met/px-vm
Динамический анализ (песочница)Обход IDS/IPSОбратная инженерияВеб-безопасностьАнализ вредоносных программКриптографияАнализ Бинарных ФайловСтатьи и ИсследованияОбучение и ОбразованиеАнти-БотПодмена Цифрового Отпечатка
5514265 месяцев назадПроверено Kitploit
GitHub
b9ph0met/px-vm

px-vm

Репозиторий

Популярное

Смотреть все →

Откройте для себя самые используемые инструменты нашего сообщества.

Изучить все инструменты

Просмотрите нашу коллекцию инструментов

Смотреть все инструменты →

Описание

Набор инструментов для обратного проектирования виртуальной машины байт-кода PerimeterX, включающий дизассемблер на основе CFG, 5-уровневый конвейер дешифрования, восстановление таблицы опкодов и очиститель эмуляции стека для исследований в области безопасности, связанных с fingerprinting обнаружения ботов.

Поделиться

Анализ VM PerimeterX Auditor

Сводка

В этом репозитории документируется обратная разработка auditor.js от PerimeterX — байткод-виртуальной машины, используемой в качестве вторичного уровня снятия отпечатков в пайплайне обнаружения ботов PX. Анализ охватывает:

  • Извлечение байткода и 5-уровневый конвейер дешифрования
  • Восстановление таблицы опкодов (107 базовых + 40 «медовых» + 24 заполняющих + 16 групп суперинструкций)
  • Дешифрование пула констант (1230 записей, 1095 зашифрованных строк)
  • Дизассемблер на основе CFG с разрешением поддиспетчеризации суперинструкций
  • Очиститель на основе эмуляции стека, создающий читаемый псевдокод
  • Антианалитические методы: медовые опкоды, перекрывающиеся инструкции, хэширование целостности кода

Примечание: Этот репозиторий охватывает только одну (статическую) версию VM и предназначен для целей исследований в области безопасности. Он не включает динамические решатели или реализации продакшн-решателей.

Предыстория

В четверг, 2 апреля 2026 года, PerimeterX развернула новую байткод-виртуальную машину в рамках своего пайплайна обнаружения ботов.

Что внутри

auditor.js не похож на обычный сенсорный скрипт PX. Вместо привычных обфусцированных поисков свойств и функций-сборщиков:

  • 8 массивных строк в base64 (_fg0 – _fg7) — зашифрованная программа VM, разбитая по переменным
  • Функция XOR-дешифрования (_dp) с посайтовым ключом (_pk), распаковывающая JSON программы
  • Перетасовка Фишера-Йетса, переставляющая таблицу опкодов так, что значения байткода различаются в разных сборках
  • Цикл диспетчеризации с 107+ обработчиками случаев — интерпретатор VM
  • Арифметика BigInt для RSA-шифрования вывода отпечатка
  • Хэш целостности кода (_0x8df7), хэширующий исходный код самой VM для вывода ключа дешифрования, так что любое изменение молча ломает дешифрование байткода

Шаг 1: Извлечение байткода

Программа VM разбита на 8 переменных, конкатенируется, а затем дешифруется функцией _dp() с использованием посайтового XOR-шифра, ключом которого является _pk:

var _pk = 893686289;
function _dp(_b) {
    var _r = atob(_b), _o = new Array(_r.length);
    for (var _i = 0; _i < _r.length; _i++) {
        _o[_i] = String.fromCharCode(
            _r.charCodeAt(_i) ^ (((_pk >>> (8 * (_i % 4))) ^ Math.imul(_i + 1, 0x6B8B4567)) & 0xFF)
        );
    }
    return _o.join("");
}

Результат — объект JSON с обфусцированными двухсимвольными именами ключей (например, "uo" для seed, "dk" для nonce). Таблица соответствия преобразует их в стандартные имена.

node extractor.js
# -> program.json

Структура программы

ПолеОписание
sSeed (12755), управляет всеми криптографическими операциями
nNonce (1603730985), рандомизация для каждой программы
gФлаг генератора, включает уровень дешифрования с хэшем целостности
xЗашифрованный флаг, константы зашифрованы XOR
cПул констант, 1230 записей
fФункции, 112 записей с зашифрованным байткодом
eТочка входа, индекс функции 0

Шаг 2: Дешифрование констант

Все 1095 строковых констант зашифрованы двумя уровнями:

Уровень 1: Статический murmur XOR с ключом 4008000571, зависит от позиции.

Уровень 2: XOR с потоком PRNG, использующим glibc LCG; seed формируется комбинацией seed программы с индексом каждой константы через мультипликативное хэширование Кнута.

Перед дешифрованием seed XORится с отпечатком окружения (_0xaf48) — 8-битной битовой маской, вычисляемой путём зондирования API браузера:

БитТестChrome
0typeof window.matchMedia === "function"1
1document.elementFromPoint существует1
2typeof window.requestAnimationFrame === "function"1
3typeof window.getComputedStyle === "function"1
4CSS.supports существует1
5navigator.sendBeacon существует1
6document.execCommand существует1
7process.versions.node существует (Node.js)0

Для Chrome: _0xaf48 = 0b01111111 = 127, что даёт эффективный seed = 12755 ^ 127 = 12716.

Это означает, что одна и та же программа даёт разные результаты дешифрования в разных средах. Запуск в Node.js, Chrome и Firefox приводит к разным seed.

node decrypt_constants.js
# -> program_decrypted.json, constants_table.txt

Что раскрывают константы

Расшифрованные строки точно говорят нам, какие отпечатки снимает VM:

Снятие отпечатков браузера: screenWidth, screenHeight, innerWidth, innerHeight, devicePixelRatio, colorDepth, platform, userAgent, language, timezone, timezoneOffset, forcedColors, highContrast

Тайминги производительности: navigationStart, domComplete, domLoading, fetchStart, requestStart, responseEnd, secureConnectionStart, serverTiming

Криптография RSA: BigInt, modPow, AQAB (65537 в base64), modulusLength, shiftLeft, shiftRight, getRandomValues

Зондирование DOM/SVG: http://www.w3.org/2000/svg, createElementNS, getBoundingClientRect, getTotalLength, getBBox

Имена полей PX: mtr, tst, mst, enc, sbx, fstec, pdc, prb, wvi, wva, pti, dis, los, cv, sc, jd, ads, enve, init

Ссылки на конечные точки: https://fst-ec.perimeterx.net/?id=

Анти-отладчик: _CMP_RCX_07;_JNZ_0x0A_EB_CC, CC|CD-04|BREAKPOINT-005

Шаг 3: Таблица опкодов

107 базовых опкодов, покрывающих весь язык JavaScript, плюс динамически генерируемый шум:

40 медовых опкодов — альтернативные реализации арифметических/сравнительных операций с математически эквивалентными, но синтаксически различными выражениями. ADD может выглядеть как (a^b) + 2*(a&b) или -((-a)-b) или a-(-b). Каждый базовый опкод может иметь до 3 вариантов, генерируемых детерминированно из seed. Простая инструкция ADD может появиться как 4 разных значения байткода в одной программе, ломая подходы на основе поиска шаблонов.

24 заполняющих опкода выделяются в перестановке, но не имеют обработчиков и никогда не генерируются. Они существуют для расширения пространства опкодов и усложнения инвертирования перетасовки.

16 групп суперинструкций — самая важная антианалитическая особенность. Когда цикл диспетчеризации разрешает опкод в лидер суперинструкции, обработчик читает один дополнительный байт из потока байткода и диспетчеризирует к подобработчику. Подобработчик может быть совершенно другой операцией:

Лидер разрешается какПодбайтФактически выполняется
FOR_IN_NEXT74FOR_IN_NEXT
FOR_IN_NEXT100MAKE_CLOSURE
ASSIGN_OP_VAR165ASSIGN_OP_VAR
ASSIGN_OP_VAR37JMP
GET_VAR_PROP_C143SET_VAR_POP
GET_VAR_PROP_C23JMP_NULLISH

Таблица опкодов перетасовывается с помощью Фишера-Йетса, инициализированного эффективным seed, так что значения байткода различаются в разных сборках.

node build_opcodes.js
# -> opcode_table.json, opcode_table.txt

Шаг 4: Построитель CFG

Ядро инструментария. cfg.js строит граф потока управления, следуя по всем путям выполнения от PC=0, декодируя каждую инструкцию с правильным контекстом шифрования.

Почему не линейный дизассемблер

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

Пятиуровневое шифрование байткода

Скачать инструмент