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

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

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

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

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

Категории

Все категории
Loading categories
CVE-2025-24990_POC — Доказательство концепции CVE-2025-24990 (драйвер Agere Systems) | Kitploit
Инструменты/GitHubGitHub/moiz-2x/cve-2025-24990_poc
Повышение привилегийФреймворки для эксплойтовАнализ уязвимостейЭксплуатацияЭксплуатация Бинарных Файлов
GitHubmoiz-2x/cve-2025-24990_poc

CVE-2025-24990_POC

Доказательство концепции CVE-2025-24990 (драйвер Agere Systems)

Репозиторий
58131411 месяцев назадПроверено Kitploit

Популярное

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

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

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

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

Смотреть все инструменты →
Поделиться

Драйвер модема Agere для Windows (ltmdm64.sys). Этот драйвер очень старый и не загружается по умолчанию на моей тестовой машине, поэтому я буду эксплуатировать его в сценарии BYOVD. Интересно, что, согласно моим исследованиям, этот драйвер существовал на Windows 7 и имеет как минимум одну ошибку. здесь

В то время MSRC не предпринял никаких действий 🤡

Уязвимости

Некоторые IOCTL в этом драйвере используют METHOD_NEITHER, но не проверяют, находится ли буфер адреса, предоставленный вызывающим абонентом, в пользовательском или режиме ядра. Вот пример кода IOCTL, который я декодировал с помощью OSR:

Это означает, что вы можете передать адрес ядра в API DeviceIoControl, и драйвер обработает его обычным образом.

Обратите внимание, что сначала нужно обойти kASLR, чтобы утечь адрес ядра. Я буду использовать EnumDeviceDrivers (в Windows 24h2 для этого нужен SeDebugPriv).

Разыменование NULL

Проблема в IOCTL 0x802b200f (ud_response). Опять же, этот диспетчер IOCTL не проверяет адрес, который я передаю из пользовательского режима, но я воспользуюсь этим позже.

ud_response вызывает ll_load_diagnostics, и я достигну следующего кода:

В начале глобальная переменная eeprom не инициализирована, поэтому она будет содержать NULL. Вот простой код, который вызовет это.

Я воспользуюсь этим позже.

Точка входа эксплойта 0x802b2003

Этот IOCTL просто преобразует строку версии драйвера "8.36" в число 0x836 (тип DWORD) и записывает его по адресу, предоставленному вызывающим абонентом (благодаря METHOD_NEITHER). Технически я могу записать эти четыре байта (36 08 00 00) по произвольному адресу ядра. Я воспользуюсь этим, чтобы перезаписать глобальные переменные драйвера и изменить поток выполнения.

Я буду называть этот 0x802b2003 IOCTL_GET_VERSION

Эксплойт

Произвольный нулевой 1 байт:

Возвращаясь к случаю разыменования NULL, я использую API VirtualAlloc для выделения фиксированного адреса (0x083600000000). Затем я использую IOCTL_GET_VERSION, чтобы записать в *(eeprom + 4) четыре байта, описанные выше. Когда драйвер позже разыменует eeprom, он прочитает данные по адресу, который я выделил.

После исправления разыменования NULL, IOCTL записывает строку по адресу, который я передаю из пользовательского режима, на основе размера буфера.

Этот код просто демонстрирует то, что я описал выше: выделяет буфер и заполняет его 0xAA, исправляет разыменование NULL, затем вызывает драйвер. Обратите внимание, что я выделяю 11 байт, но передаю драйверу размер буфера только 10, чтобы посмотреть, как он себя поведет.

Он записывает фиксированную последовательность байтов в мой буфер, а затем обнуляет последний байт (11-й), даже если я предоставляю размер только 10. Он заменяет последний 0xAA в моем буфере на 0x00. Это указывает на то, что если я укажу размер 0, драйвер все равно запишет один байт 0x00 по целевому адресу.

Произвольное уменьшение

Теперь у меня есть нулевой и произвольный с фиксированными 4 байтами, давайте создадим другой примитив.

Этот IOCTL установит глобальный LtMsgEvent в мой пользовательский буфер, затем проверит, является ли WDM нулевым, и снова установит ноль.

Затем в 0x802b2207 он вызовет API ObfReferenceObject.

В начальном состоянии WDM равен нулю, но с помощью IOCTL_GET_VERSION я могу установить WDM в 0x36 (его размер всего 1 байт), а LtMsgEvent все еще мой буфер. Затем я обнулю WDM и вызову 0x802b2207. Наконец, достигну ObfReferenceObject. Я буду называть эти два ioctl IOCTL_SET_LtMsgEvent и IOCTL_DEREF_LtMsgEvent.

Техника эксплойта с использованием ObfReferenceObject изменяет PreviousMode нашего KTHREAD с UserMode на KernelMode. Вы можете прочитать об этом здесь). Однако Windows исправила этот эксплойт, поэтому мы не можем его использовать.

Но примитив в ObfReferenceObject все еще существует. API вычитает 0x30 из предоставленного нами адреса, приводит результат к 8-байтовому целому числу, а затем вычитает 1.

*(signed long long)(LtMsgEvent-0x30) -= 1

Но проблема в том, что он проверяет, является ли следующее значение 0 или текущее значение < 1 (интерпретируется как 8-байтовое целое число со знаком). Если какое-либо из условий истинно, он переходит к KeBugCheckEx и вызывает сбой системы.

Произвольная запись

Имея в руках произвольное уменьшение, мне нужно найти другое место для записи байта 0xFF, а затем уменьшить его до нужного мне байта, и я нашел этот ioctl 0x802b2243:

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