能力值:
( LV2,RANK:10 )
|
-
-
2 楼
我没有接触(看过)壳技术中有关双进程的文章,不过按小第的推测(这个方法我已经想到了,小弟正要在自己的壳中去实现)既然是关于自己进程以外的其他进程,一定是将壳里的代码注入到其他进程里去的,只需要VirtualAllocEx,CreateRemoteThread这两个函数来实现,代码在其他进程中执行可以有效防止被跟踪.如果再有一个进程对注入其他进程中的代码进行解码(试想第一个注入其他的进程代码是被加过密的,不然静态分析就看出来了),此外还可以在远程线程里检测OD之类软件的运行,又可以进一步对软件进行保护.呵呵,如果这样做出来,分析起来应该很难.嘿嘿
|
能力值:
( LV9,RANK:450 )
|
-
-
3 楼
其实一般的双进程只是为了anti debug.解码还是本进程完成的.所以大多可以patch单
|
能力值:
( LV2,RANK:10 )
|
-
-
4 楼
解码的代码用在自己的进程里不就清楚的知道了 解码的算法步骤 了么,我觉得互相进行解码比较好,只是复杂些
|
能力值:
( LV6,RANK:90 )
|
-
-
5 楼
多谢指教,对付这一类的壳应该是利用进程的通信作为切入点吧~
|
能力值:
( LV2,RANK:10 )
|
-
-
6 楼
这位兄弟,我最近也在写双进程的壳,快完成了,在这里又遇到几个技术问题,想与你讨论一下,第一个就是LoadLibrary的问题,我的填IAT表的部分在 另一个远程线程内执行,但是呢,无法给宿主进程加载DLL,这就需要我自己写一个可以跨进程的LoadLibrary.怎么写呢?一时间还没有一点点思路.再有一个惊喜就是,我发现双进程的壳只要做一点工夫 可以绝对免动态,一动态就立即重新启动计算机了,这样的壳破解难度会加大.
|
能力值:
( LV2,RANK:10 )
|
-
-
7 楼
说起可能没多少参考价值的,下面发一部分代码给你看下,可能对你有一定帮助.
下面这段代码是我实现双进程的一个部分,是将代码插入进去.被插入的代码首先会调用一个子函数,这个子函数用于寻找API.当然所有的代码都是重定位处理的.
其他的还有两个子函数是用在远程线程上的,还没测试好,所以不敢发,有兴趣可以找我,一起研究下
Inject_Code proc uses edi esi ebx dwProtect:DWORD,codesize:DWORD,Run:DWORD,RunAddr:DWORD,Reset:DWORD
LOCAL p32:PROCESSENTRY32
LOCAL m32:MODULEENTRY32
LOCAL hShot:DWORD
LOCAL buf[255]:BYTE
LOCAL hMem:DWORD
LOCAL hMod:DWORD
LOCAL curProcess:DWORD
LOCAL hThread:DWORD
LOCAL dwCount:DWORD
and dwCount,0
push NULL
push TH32CS_SNAPPROCESS
call DWORD ptr [ebx+CreateToolhelp32Snapshot1]
test eax,eax
jnz @f
jmp @ERROR_EXIT
@@:
mov hShot,eax
mov p32.dwSize,sizeof PROCESSENTRY32
lea eax,p32
push eax
push hShot
call DWORD ptr [ebx+Process32First1]
.while eax
mov eax,p32.th32ProcessID
mov edx,eax
.if eax==dwProtect || edx==0
;跳过参数中指明不进行的
jmp _continue
.endif
;mov edx,Reset
;.if eax<1000 && edx<=0
;跳过系统进程和服务进程
;jmp _continue
;.endif
mov eax,p32.th32ProcessID
push eax
push NULL
push PROCESS_ALL_ACCESS
call DWORD ptr [ebx+ OpenProcess1]
.if eax==NULL
jmp _continue
.endif
mov curProcess,eax
lea eax,[ebx+dwTemp]
push DUPLICATE_SAME_ACCESS
push NULL
push PROCESS_VM_OPERATION or PROCESS_VM_WRITE or PROCESS_VM_READ
push eax
push curProcess
push DWORD ptr [ebx+hProcess]
push DWORD ptr [ebx+hProcess]
call DWORD ptr [ebx+DuplicateHandle1]
push DWORD ptr [ebx+dwTemp]
pop DWORD ptr [ebx+sProcess]
push PAGE_EXECUTE_READWRITE
push MEM_COMMIT or MEM_RESERVE
push codesize
push NULL
push curProcess
call DWORD ptr [ebx+ VirtualAllocEx1]
or eax,eax
jz @ERROR_EXIT
mov hMem,eax
lea eax,[ebx+EggShell_Startup]
push NULL
push codesize
push eax
push hMem
push curProcess
call DWORD ptr [ebx+ WriteProcessMemory1]
or eax,eax
jz @ERROR_EXIT
mov edx,Run
.if edx>0
;mov edx,hMem
mov edx,RunAddr
lea eax,[ebx+EggShell_Startup]
sub edx,eax
mov eax,hMem
add edx,eax
lea eax, hThread
push eax
push 0
push NULL
push edx
push 0
push NULL
push curProcess
call DWORD ptr [ebx+CreateRemoteThread1]
.if eax<=0
push MEM_RELEASE
push 0
push hMem
push curProcess
call DWORD ptr [ebx+ VirtualFreeEx1]
xor eax,eax
jmp _continue
.endif
inc dwCount
mov edx,Run
.if dwCount>=edx
.break
.endif
mov hThread,eax
.endif
_continue:
mov p32.dwSize,sizeof PROCESSENTRY32
lea eax,p32
push eax
push hShot
call DWORD ptr [ebx+Process32Next1]
.endw
push hShot
call DWORD ptr [ebx+CloseHandle1]
mov eax,dwCount
@ERROR_EXIT:
ret
Inject_Code endp
下面是一个调用的例子,有注释,你只要一看就明白函数功能了
call DWORD ptr [ebx+GetCurrentProcessId1]
lea edx,[ebx+EggShell_Startup]
lea ecx,[ebx+Inject_1]
push 0 ;是否重新启动计算机
push ecx ;远程线程的入口点函数地址
push 1 ;是否执行远程线程(大于0),和远程线程的数量(将接近不大于用户进程的数量)
push EggShell_End-EggShell_Startup ;代码长度
push eax ;指明不操作的进程ID,-1代表所有进程都要操作
call Inject_Code
|