能力值:
( LV3,RANK:30 )
|
-
-
3 楼
刚追了一下,眼睛开始流泪了 (所以很久都不碰这些东西了) ,珍惜生命,远离解密 。。。。。再反追一下估计可以还原的 。。。暂时如下
输入 12345678 , 结果是 4f d1 89 57
4BB7A3F0 - D49A9B6D = 771D0883
771D0883 + 88E2F7E5 = 68
4BB7A3F0 - D49A9B6D = 771D0883
771D0883 + 88E2F7EF = 72
4BB7A3F0 - D49A9B6D = 771D0883
771D0883 + 88E2F842 = C5
4BB7A3F0 - D49A9B6D = 771D0883
771D0883 + 88E2F858 = DB
上面的 68 72 C5 DB 再经下面的最后解码的出 4f d1 89 57
00415F99 mov al, byte ptr ss:[ebp-0xF8]
00415F9F or al, byte ptr ss:[ebp-0x104]
00415FA5 mov cl, byte ptr ss:[ebp-0xF8]
00415FAB and cl, byte ptr ss:[ebp-0x104]
00415FB1 add al, cl
00415FB3 mov byte ptr ss:[ebp-0xF8], al
|
能力值:
( LV2,RANK:15 )
|
-
-
7 楼
您好,眼睛不舒服就早点休息吧, 明个有空我们再来讨论, 我目前大概知道您已经走到哪一步了,您应该是到了生成KEY,加密那一步了。 但那只是2个函数的调用过程, 我特意留下没有使用SVMP虚拟化的, 因为总得留下线索,其实在更前面的位置,就已经有了这两个函数的线索。但是了,这两个函数的里面的代码是经过SVMP虚拟化了的,关键是看您能不能还原出实现代码,当然完全一模一样也没有必要, 您只要还原出大概的,或者是相同的功能, 给出几个指令handler也算是可以了。
然后就是您应该也看了这两个函数之后的一个过程,是被SVMP虚拟机保护了的, 然后才到printf. 您应该更具堆栈得知加密后的数据再一次经过了处理, 然后您还给出了代码, 但是那段代码是错误的,
但或许您指的 [ebp-0xf8] [ebp-0x104] 是您自己写出来的代码, 没有给出具体输入输出所以我也没有办法写代码验证您的答案, 至于最上面的 + -表达式, 我是真的一点都没有看明白, 还请您给于指点一下。
早点休息吧, 晚安。
|
能力值:
( LV3,RANK:30 )
|
-
-
10 楼
上面加法产生在下面的代码处,昨天是正向追踪的,也发现里面的结构啊什么的,但实在怕麻烦,没有分析下去了,但是没能搞清楚,毕竟繁杂了,这和 vmp 不同,那东西搞了很久,很多东西都给时间磨平了 。。。。。 并且还是当年热情高涨的时候
00406960 > mov ecx, dword ptr ss:[ebp-0x3C4]
00406966 . sub ecx, dword ptr ss:[ebp-0x3C8]
0040696C . mov edx, dword ptr ss:[ebp-0x14A0]
00406972 . add ecx, dword ptr ds:[edx] 昨天贴的那个记录就是从这,用脚本上记录下来的
00406974 . mov dword ptr ss:[ebp-0x374], ecx
随手写了个,还不保证有错误,试了一下感觉ok .... 分析真是累人的活
楼主这坑挖的深啊,强大,哪里学的 。。。。。。难道是 。。山东济。。。
刚才测试了一下,貌似有很小部分得出结果不一致 (等我修改一下)
|
能力值:
( LV2,RANK:15 )
|
-
-
11 楼
原来你是在这里记录的, 这里是从虚拟CPU里面取出一个数据或是转换一个数据时做的操作, 你发出来的这几行代码是一个虚拟CPU数据的加密解密过程, 这些代码在全局里面都会包含, 就这个位置往下走才是handler。
输入的加密解决绝不是这里, 这里只是一个虚拟CPU原子操作地点, 一条指令不见得会来一次。
原始代码在PE文件里面肯定是没有了的, 写注册机不需要逆向都可以, 你只要从00 到 ff 依次输入观察加密后的数据 就可以很简单的实现注册机了。
我们不看结果,只看对原始代码还原的程度。
另外您写的这个注册机, 只是针对了我这一个KEY, 我不需要修改生成KEY 跟加密解密的代码,只需要修改初始化子KEY的代码, 您的注册机就会失效。
您想一下, 我这里使用的是32字节的子KEY, 您需要写多少注册机才能应付所有的输入输出?
您目前并不是通过源代码来写出注册机,完全是靠猜测的,因为您应该是还没有解决创建KEY那一块代码。
关于第一层函数源代码我发出来, 有助于您分析,该函数内部所有的call 均使用Function代替原始函数名:
VOID __declspec(naked)Function(VOID){
__asm push ebp;
__asm mov ebp, esp;
__asm sub esp, 0x428;
__asm push eax;
__asm push ebx;
__asm push ecx;
__asm push edx;
__asm push esi;
__asm push edi;
// 需要加密的代码段 这里我简单的生成子KEY 非常简单的代码[您可以依据这里分析虚拟机]
SYS_PROTECT_BEGIN('f', 'o', 'r', 'c', 'o', 'd', 'e', 0, 0);
__asm xor ecx, ecx;
__asm jmp __for_key_cmp;
__for_key_start:
__asm add ecx, 0x1;
__for_key_cmp:
__asm cmp ecx, 32;
__asm je __for_key_end;
__asm lea eax, dp[ebp - 0x20];
__asm mov bp[eax + ecx], cl;
__asm jmp __for_key_start;
__for_key_end:
SYS_PROTECT_END();
// 生成key
__asm push 32;
__asm lea edx, dp[ebp - 0x20]; // 子KEY
__asm push edx;
__asm lea edx, dp[ebp - 0x428]; // 生成的EKY
__asm push edx;
__asm call dp[Function]; // 生成KEY的函数 [该函数内部使用SVMP加密]
__asm add esp, 0xc;
// 加密
__asm push 4;
__asm mov edx, dp[ebp + 0x8]; // 加密的字节 也就是 0x12345678 您输入的
__asm push edx;
__asm lea edx, dp[ebp - 0x428]; // KEY
__asm push edx;
__asm call dp[Function]; // 加密函数 [该函数内部使用SVMP加密]
__asm add esp, 0xc;
// 需要加密的代码段
SYS_PROTECT_BEGIN('a', 'd', 'd', 'c', 'o', 'd', 'e', 0, 0);
// 额外加
__asm mov al, 0xef;
__asm mov ecx, dp[ebp + 0x8];
__asm add bp[ecx + 0x0], al;
__asm mov al, 0x17;
__asm add bp[ecx + 0x1], al;
__asm mov al, 0x0c;
__asm add bp[ecx + 0x2], al;
__asm mov al, 0x74;
__asm add bp[ecx + 0x3], al;
SYS_PROTECT_END();
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x0];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x1];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x2];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x3];
__asm push edx;
__asm lea edx, dp[g_Msg];
__asm push edx;
__asm call dp[printf];
__asm add esp, 0x14;
// 生成key
__asm push 32;
__asm lea edx, dp[ebp - 0x20];
__asm push edx;
__asm lea edx, dp[ebp - 0x428];
__asm push edx;
__asm call dp[Function];
__asm add esp, 0xc;
// 需要加密的代码段
SYS_PROTECT_BEGIN('s', 'u', 'b', 'c', 'o', 'd', 'e', 0, 0);
// 额外减
__asm mov al, 0xef;
__asm mov ecx, dp[ebp + 0x8];
__asm sub bp[ecx + 0x0], al;
__asm mov al, 0x17;
__asm sub bp[ecx + 0x1], al;
__asm mov al, 0x0c;
__asm sub bp[ecx + 0x2], al;
__asm mov al, 0x74;
__asm sub bp[ecx + 0x3], al;
SYS_PROTECT_END();
// 解密
__asm push 4;
__asm mov edx, dp[ebp + 0x8];
__asm push edx;
__asm lea edx, dp[ebp - 0x428];
__asm push edx;
__asm call dp[Function];
__asm add esp, 0xc;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x3];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x2];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x1];
__asm push edx;
__asm mov edx, dp[ebp + 0x8];
__asm movzx edx, bp[edx + 0x0];
__asm push edx;
__asm lea edx, dp[g_Msg];
__asm push edx;
__asm call dp[printf];
__asm add esp, 0x14;
__asm pop edi;
__asm pop esi;
__asm pop edx;
__asm pop ecx;
__asm pop ebx;
__asm pop eax;
__asm add esp, 0x428;
__asm pop ebp;
__asm ret;
}
期待您把创建KEY的注册机也写出来,希望您从还原原始代码下手。
|
能力值:
( LV2,RANK:15 )
|
-
-
13 楼
00F51E1F push esp
00F51E20 push ebp
00F51E21 push eax
00F51E22 push ebx
00F51E23 push ecx
00F51E24 push edx
00F51E25 push esi
00F51E26 push edi
00F51E27 pushfd
00F51E28 sub esp,0x6C ; 'l'
00F51E2B wait
00F51E2C fsave [esp]
00F51E2F push 0x1000
00F51E34 call malloc (00F62DCC)
00F51E39 add esp,4
00F51E3C add esp,0x6C ; 'l'
00F51E3F add eax,0x1000
00F51E44 mov esi,esp
00F51E46 sub esi,0x6C ; 'l'
00F51E49 mov edi,eax
00F51E4B sub edi,0x90
00F51E51 mov ecx,0x1B
00F51E56 rep movsd
00F51E58 pop [eax-0x24]
00F51E5B pop [eax-0x20]
00F51E5E pop [eax-0x1C]
00F51E61 pop [eax-0x18]
00F51E64 pop [eax-0x14]
00F51E67 pop [eax-0x10]
00F51E6A pop [eax-0xC]
00F51E6D pop [eax-0x8]
00F51E70 pop [eax-0x4]
00F51E73 push eax
00F51E74 call sub_00F51E7B (00F51E7B)
00F51E79 jmp sub_00F51E7B+0x5 (00F51E80)
00F51E7B mov eax,[esp]
00F51E7E push eax
00F51E7F ret
00F51E80 lea edx,[MainFor (00F80610)]
00F51E86 push edx
00F51E87 call SysVMProtectFunction (00F52D40)
00F51E8C add esp,4
00F51E8F pop eax
00F51E90 pop eax
00F51E91 mov edi,[eax-0x24]
00F51E94 push edi
00F51E95 popfd
00F51E96 mov edi,[eax-0x20]
00F51E99 mov esi,[eax-0x1C]
00F51E9C mov edx,[eax-0x18]
00F51E9F mov ecx,[eax-0x14]
00F51EA2 mov ebx,[eax-0x10]
00F51EA5 push esi
00F51EA6 mov esi,eax
00F51EA8 sub esi,0x90
00F51EAE push edi
00F51EAF push ecx
00F51EB0 sub esp,0x6C ; 'l'
00F51EB3 mov edi,esp
00F51EB5 mov ecx,0x1B
00F51EBA rep movsd
00F51EBC frstor [esp]
00F51EBF add esp,0x6C ; 'l'
00F51EC2 pop ecx
00F51EC3 pop edi
00F51EC4 pop esi
00F51EC5 push edi
00F51EC6 mov edi,[eax-0xC]
00F51EC9 pushad
00F51ECA pushfd
00F51ECB sub eax,0x1000
00F51ED0 push eax
00F51ED1 call free (00F62D94)
00F51ED6 add esp,4
00F51ED9 popfd
00F51EDA popad
00F51EDB mov eax,edi
00F51EDD pop edi 上面这段代码, 就是:
SYS_PROTECT_BEGIN(...);
SYS_PROTECT_END();
包含的代码被SVMP的编译器提取出来后插入的虚拟机入口代码, 这入口是很明显的.
然后原始代码是被svmp的编译器删除了的, 所以里面肯定不会有源代码, 您最早之前的 + -法肯定不是加密函数的源代码。
不过您刚才说的地址记录, 我到是想到了一个安全隐患, 真的非常感谢您的无私奉献,下一次更新我将完全重写虚拟CPU的读写方式。
在此感谢您,希望您可以继续分析下去, 在给俺挖点坑出来,
|