Программирование в машинных кодах или soft-ice как logger

точка останова, шпионящая за открытием файлов, начинающихся с буквы 'a'


Проблема в том, что если функции CreateFileA передается полное имя файла с путем, наша точка останова уже не сработает, поскольку она проверяет только первый символ имени, а функции поиска подстроки в арсенале soft-ice увы, нет. Как говориться, конструктивно непредусмотрено. Какая жалость, но… хакеры мы или нет?!

Будем исходить из того, что память, лежащая выше указателя стека, как правило свободна и может быть использована по нашему усмотрению. Что если записать туда крошечную ассемблерную программу и передать на нее управление? Если это получится (а это получится, уж поверьте мне, парни) мы сможем неограниченно наращивать функционал отладчика, не прибегая к плагинам, которые не совсем документированы (точнее, совсем не документированы), довольно громоздки, неповоротливы и т. д.

Для выполнения программы на стеке нам очевидно нужен исполняемый стек. Вплоть до настоящего времени это не представляло проблемы и в стеке можно было выполнять любой код без каких бы то ни было ухищрений, но теперь ситуация изменилась и на пике борьбы с вирусами и сетевыми червями, производители процессоров скооперировались с Microsoft и в последних версиях Windows XP, а так же ненавистной мне Longhorn, по умолчанию стек защищен от исполнения, впрочем, при первой же попытке выполнения машинного кода в его окрестностях, система выбрасывает диалоговое окно, предлагающее либо отключить защиту, либо сделать нехорошей программе харакири.

Чтобы осуществить задуманное, мы должны сделать следующее:

q       поместить машинный код нашей функции выше вершины стека;

q       сохранить текущее значение регистра EIP и регистра флагов (например, в том же стеке);

q       сохранить все регистры, которые изменяет наша функция;

q       установить EIP на начало нашей функции;

q       тем или иным образом передать аргументы (например, через регистры);


q       выполнить функцию, возвратив результат работы например через EAX;

q       проанализировать возвращенное значение, выполнив те или иные операции;

q       восстановить измененные регистры;

q       восстановить регистр EIP и регистр флагов;

q       продолжить нормальное выполнение программы.

Звучит устрашающе, но ничего сложного в этом нет. Давайте для начала попытаемся выполнить функцию XOR EAX,EAX/RET. Как перевести ее в машинный код? Можно, конечно, воспользоваться HIEW'ом или даже FASM'ом, но зачем выходить из soft-ice? Достаточно переместиться в любое свободное место памяти и дать команду 'a' (assemble – то есть ассемблировать), только предварительно убедитесь, что вы находитесь в контексте отлаживаемого приложения (его имя отображается в правом нижнем углу экрана), а не в ядре, иначе случится крах.

:a esp-10

0023:0012B0DC xor eax,eax

0023:0012B0DE ret

0023:0012B0DF

:d esp-10

0023:0012B0DC 33 C0 C3 00 DB 80 FB 77-88 AE F8 77 FF FF FF FF  3......w...w....

0023:0012B0EC 31 D8 43 00 E8 59 48 00-00 00 00 C0 03 00 00 00  1.C..YH.........


Содержание раздела