Первый вирь - COMом

Xakep, номер #014, стр. 014-058-5


Что в имени тебе моем - ты оцени груди объем!

Весьма актуальная тема. :) Вирус должен быть небольшим, а вирус на асме - просто обязан таковым быть. Поэтому я скажу несколько слов об оптимизации. Сам процесс довольно увлекателен (патологоанатомы тоже считают свою работу - увлекательной :)), поскольку заставляет крутиться шарики в черепной коробке немного быстрее, чем обычно. Хороший пример - использование LEA вместо MOV DX,ADDR; ADD DX,BP. Кроме того, команда присвоения регистр-регистр обычно занимает два байта. А ведь можно обойтись одним, если значение в регистре-источнике больше не понадобится. Как именно? Пока подумай сам, а я замечу, что кроме, например, OR AX,AX - проверки того, что AX = 0, существует еще и DEC AX, которая вполне сыграет ту же роль, если значение в AX в дальнейшем все равно пропадет.

Ну что, еще не догадался как присвоить регистр-регистр одним байтом?

Доктор, я буду жить?

Чтобы файл открыть, нужно знать его имя. Так как нигде я не использовал такие функции, как CHDIR и GETCURRENTDIR, то имя должно быть полным, чтобы файлы открывались не только в текущем, но и в родительском каталоге, и в подкаталогах. В процессе поиска вирь должен подправлять значение текущего каталога соответственно тому, где он файлы ищет. Потом к этому каталогу добавляется имя "найденыша". Вот такие чебуреки.

Что-то я отвлекся. Вернемся к нашим... эээ... паразитам. :) Жертва есть, значит хакер ее заразит. Первым делом, прочитать первые три байта в специально отведенную для этой цели область - она должна быть включена в тело вируса, в отличие от всяких временных данных, вроде областей DTA. Затем нужно перескочить в конец вируса (снова концы да концы - пошляк :)) и прочесть там два байта. Ведь перед тем как заразить, нужно проверить - не заразный (в смысле, не зараженный) ли уже этот файл. Проверить это достаточно просто - поместить в конец тела вируса какую-нибудь метку. Если потом в потенциальной жертве (файле) метка присутствует - значит файл заражен.

Я сначала считываю первые три байта просто, чтобы не гонять указатель по файлам лишний раз. Программирование должно быть экономным! Затем, начиная с конца файла, помещается собственно сам Его Величество Толстопопый I. :) Уютно поместившись в конце файла, правим первые три байта жертвы не JMP`ом, а CALL`ом на себя! CALL намного удобней! Когда это КАЛЛ был удобен? Было и такое время :).

Вопрос: Так как же все-таки установить одним байтом?

Ответ: XCHG Регистр,Регистр. То есть вместо

mov ax,bx

вполне можно написать

xchg ax,bx

если bx больше не нужен.

Все, хакер может звать юзеров - пусть приносят винты, он будет выгуливать зверушку. Листинг твари прилагается. Желаю удачи. :)

; ComXakep-вирь занимает ровно 512 байт, вместе с "личинкой" 512+4=516 байт.

; написан специально для журнала Хакер

; для использования исключительно

; в образовательных целях (то-то во всей редакции винты упали :)).

code segment byte public

assume cs:code,ds:code,es:code,ss:code

Назад на стр. 014-058-4  Содержание  Вперед на стр. 014-058-6