Издательский дом ООО "Гейм Лэнд"ЖУРНАЛ ХАКЕР #86, ФЕВРАЛЬ 2006 г.

WMF: баг года

крис касперски ака мыщъх

Хакер, номер #086, стр. 086-066-7


К заголовку примыкает первая фреймовая запись, содержащая вызов функции META_ESCAPE (код 626h) с подфункцией SETABORTPROC (код 0009h), принимающей два параметра: дескриптор контекста устройства (в данном случае равен 16h, но может быть любым) и машинный код, которому будет передано управление, то есть shell-код. Коды всех документированных функций описаны в WINGDI.H (см. "/* Metafile Functions */"), там же можно найти и Escape-последовательности.

Дизассемблирование GDI32.DLL показывает, что Windows считывает только младший байт функции (для Escape это 26h), а в старшем передает количество параметров, которое никто не проверяет! Таким образом, чтобы распознать зловредный wmf-файл, необходимо проанализировать все фреймовые записи в поисках функции 26h, подфункции 9h.

Размер фреймовой записи необязательно должен соответствовать действительности, а также совершенно необязательно вставлять замыкающую фреймовую запись, как того требует wmf-спецификация, поскольку, когда shell-код получит управление, все спецификации идут лесом.

Что же касается самого shell-кода, то он вполне стандартен. Ильфак определяет базовый адрес KERNEL32.DLL через PEB, (что не работает на 9x), разбирает таблицу экспорта, находит адрес API-функции LoadLibraryA, загружает USER32.DLL и выводит «ругательство» через MessageBoxA. Чтобы shell-код работал, под 9x необходимо переписать функцию GetKrnl32addr, научив ее находить KERNEL32.DLL прямым поиском в памяти. Мы уже писали об этом в статье «Техника написания переносимого shell-кода», так что не будем повторяться, а лучше разберем другой эксплойт, который будет посложнее.

Пусть это будет Metasploit Framework ( его можно скачать с www.metasploit.com или взять на нашем диске). Это полиморфный эксплойт, с движком целиком написанным на Перле, способный нести любую боевую начинку в переменной PayLoad.

Генерация wmf-файла происходит так же, как и прошлый раз, только теперь некритичные поля выбираются случайно, а сам shell-код внедряется в произвольное место между «мусорными» фреймами, что ослепляет примитивные сканеры и брандмауэры. Последовательность 26h ?? 09h 00h остается постоянной, но она слишком коротка для обнаружения, а разбирать все фреймы вручную сможет только специальным образом написанный сканер.

Маленький нюанс: у Ильфака shell-код располагается за незначащим словом hDC, а в Metasploit'е он следует сразу же за подфункцией SETABORTPROC, во всяком случае так кажется при беглом анализе листинга. Переменная $shellcode состоит из двух частей: фиктивного поля Space и боевой начинки, расположенной ниже.

Чтобы написать свой эксплойт, необходимо сгенерировать wmf-заголовок, дописать фреймовую запись META_ESCAPE/SETABORTPROC и прицепить shell-код. В исходных текстах wmf-checker'а содержится файл wmfhdr.wmf, в котором уже есть заголовок и готовый фрейм. Не хватает только боевой начинки, но это легко исправить командой copy /b wmfhdr.wmf + shell-code.bin exploit.wmf, где shell-code.bin - любой shell-код, выдернутый из червя или разработанный самостоятельно.

Назад на стр. 086-066-6  Содержание  Вперед на стр. 086-066-8