明天台版的潘朵拉傳奇就要OB了,在這兒發個CB能用的多開。
抱歉我住台灣,所以貼的是繁體字。如有需要…請自行轉為簡體。
這次iplayer代理的這個潘朵拉並沒有神盾,所以也就給了我機會。希望可以弄個精華變成正式會員囉!
首先看看程式的入口點:
代码:
.text:0040D6E0 public fakeoep .text:0040D6E0 fakeoep proc near .text:0040D6E0 000 push offset realoep .text:0040D6E5 004 push offset fakeoep .text:0040D6EA 008 call launcher .text:0040D6EF 008 add esp, 8 .text:0040D6F2 000 retn .text:0040D6F2 fakeoep endp
代码:
.text:0040D6E0 000 jmp realoep
代码:
if (!CreateProcess(NULL, szExeCmd, NULL, NULL, FALSE, DEBUG_PROCESS | DEBUG_ONLY_THIS_PROCESS, NULL, szExeDir, &startInfo, &procInfo)) return EXIT_FAILURE; DEBUG_EVENT debugEvent; DWORD nStatus; CONTEXT context; LPVOID startAddr; // fakeoep LPVOID targetAddr; // realoep BYTE bStart = 0xCC; BOOL blFirstTime = TRUE; while (WaitForDebugEvent(&debugEvent, INFINITE)) { nStatus = DBG_EXCEPTION_NOT_HANDLED; if (debugEvent.dwDebugEventCode == EXIT_PROCESS_DEBUG_EVENT) break; else if (debugEvent.dwDebugEventCode == EXCEPTION_DEBUG_EVENT) { if (debugEvent.u.Exception.ExceptionRecord.ExceptionCode == EXCEPTION_BREAKPOINT) { if (blFirstTime) { // ... blFirstTime = FALSE; } else if (debugEvent.u.Exception.ExceptionRecord.ExceptionAddress == startAddr) { // ... context.ContextFlags = CONTEXT_CONTROL; GetThreadContext(procInfo.hThread, &context); context.Eip = (DWORD)targetAddr; SetThreadContext(procInfo.hThread, &context); } } nStatus = DBG_CONTINUE; } if (!ContinueDebugEvent(procInfo.dwProcessId, procInfo.dwThreadId, nStatus)) break; }
如果直接修改執行檔的內容,會發現無論如何,都會跳出「請從客戶端文件啟動」的視窗,這其實是因為CRC檔案驗證的關係。
在MessageBoxW下斷點,觸發後可以看到:
代码:
.text:0040D464 loc_40D464: ; uType .text:0040D464 994 push ebx .text:0040D465 998 push offset Caption ; lpCaption .text:0040D46A 99C push eax ; lpText .text:0040D46B 9A0 push ebx ; hWnd .text:0040D46C 9A4 call ds:MessageBoxW
代码:
.text:0040D43E loc_40D43E: .text:0040D43E 994 cmp al, bl .text:0040D440 994 jz short loc_40D491
代码:
.text:007AC0E5 loc_7AC0E5: .text:007AC0E5 030 mov eax, [ebp+arg_0] .text:007AC0E8 030 push 0 ; hTemplateFile .text:007AC0EA 034 push esi ; dwFlagsAndAttributes .text:007AC0EB 038 push [ebp+dwCreationDisposition] ; dwCreationDisposition .text:007AC0EE 03C mov dword ptr [eax], 1 .text:007AC0F4 03C mov eax, [ebp+arg_4] .text:007AC0F7 03C mov [eax], edi .text:007AC0F9 03C lea eax, [ebp+SecurityAttributes] .text:007AC0FC 03C push eax ; lpSecurityAttributes .text:007AC0FD 040 push [ebp+dwShareMode] ; dwShareMode .text:007AC100 044 push [ebp+lDistanceToMove] ; dwDesiredAccess .text:007AC103 048 push [ebp+lpFileName] ; lpFileName .text:007AC106 04C call ds:CreateFileW
代码:
.text:0079747B loc_79747B: .text:0079747B 22C mov [ebp+var_1C], 0 .text:00797481 22C push offset off_83AF48 ; wchar_t * .text:00797486 230 lea eax, [ebp+var_21C] .text:0079748C 230 push eax ; wchar_t * .text:0079748D 234 call __wfopen
代码:
.text:0079751B 22C mov word ptr [eax], 0FFFFh ; ... .text:00797530 loc_797530: .text:00797530 22C movzx cx, byte ptr [edx+edi] .text:00797535 22C xor [eax], cx .text:00797538 22C xor ecx, ecx .text:0079753A 22C mov cx, [eax] ; ... .text:00797542 22C shr cx, 1 .text:00797545 22C xor ecx, 8408h ; ... .text:0079760D loc_79760D: .text:0079760D 22C mov [eax], cx .text:00797610 22C inc edx .text:00797611 22C cmp edx, ebx .text:00797613 22C jb loc_797530
代码:
.text:007981AB 048 mov ecx, [esp+48h+arg_C] .text:007981AF 048 push edi .text:007981B0 04C lea eax, [esi+0B4h] .text:007981B6 04C push eax .text:007981B7 050 push ecx .text:007981B8 054 call sub_7973D0
代码:
.text:007981B8 054 mov word ptr [eax], 929h
解除了檔案的驗證之後,接下來要啟用多開的功能,簡單來說呢,就是當CreateMutex時,將參數MutexName改為NULL就可以了。首先,在CreateMutexW設斷點:
代码:
.text:00759B48 004 mov ecx, [esp+4+lpName] .text:00759B4C 004 movzx edx, [esp+4+arg_0] .text:00759B51 004 push ecx ; lpName .text:00759B52 008 push edx ; bInitialOwner .text:00759B53 00C push 0 ; lpMutexAttributes .text:00759B55 010 call ds:CreateMutexW
代码:
.text:00759B48 004 xor ecx, ecx .text:00759B4A 004 nop .text:00759B4B 004 nop