明可明非常明第二波cm算法分析
本帖最后由 missviola 于 2009-12-31 08:57 编辑【破文标题】明可明非常明第二波算法分析
【破文作者】missviola
【破解工具】PEID OD
【破解平台】Windows XP
【原版下载】见附件
【破解声明】只是感兴趣,没有其他目的。失误之处敬请诸位大侠赐教!
------------------------------------------------------------------------
【破解过程】首先PEID查壳,显示加了upx的壳。用upx自带的-d参数脱掉以后,显示为Borland Delphi 6.0 - 7.0。OD载入,用F12暂停法,在467996这里下断点。输入name:pediy,code:123456。分析如下:
00467996|.55 push ebp
00467997|.68 3D7A4600 push 00467A3D
0046799C|.64:FF30 push dword ptr fs:
0046799F|.64:8920 mov dword ptr fs:, esp
004679A2|.8D55 FC lea edx, dword ptr
004679A5|.8B83 F8020000 mov eax, dword ptr
004679AB|.E8 94BBFCFF call 00433544
004679B0|.837D FC 00 cmp dword ptr , 0 ;是否输入了用户名
004679B4|.74 5F je short 00467A15
004679B6|.8D55 F8 lea edx, dword ptr
004679B9|.8B83 FC020000 mov eax, dword ptr
004679BF|.E8 80BBFCFF call 00433544
004679C4|.837D F8 00 cmp dword ptr , 0 ;是否输入了注册码
004679C8|.74 4B je short 00467A15
004679CA|.8D55 F4 lea edx, dword ptr
004679CD|.8B83 FC020000 mov eax, dword ptr
004679D3|.E8 6CBBFCFF call 00433544
004679D8|.8B45 F4 mov eax, dword ptr
004679DB|.50 push eax
004679DC|.8D55 F0 lea edx, dword ptr
004679DF|.8B83 F8020000 mov eax, dword ptr
004679E5|.E8 5ABBFCFF call 00433544
004679EA|.8B45 F0 mov eax, dword ptr
004679ED|.50 push eax
004679EE|.E8 8DFFFFFF call <jmp.&hanyu.Reg1>
F7跟进4679EE处的call看看:
003CD14C >55 push ebp
003CD14D 8BEC mov ebp, esp
003CD14F 53 push ebx
003CD150 8B45 08 mov eax, dword ptr
003CD153 E8 C075FBFF call 00384718
003CD158 8B45 0C mov eax, dword ptr
003CD15B E8 B875FBFF call 00384718
003CD160 33C0 xor eax, eax
003CD162 55 push ebp
003CD163 68 BAD13C00 push 003CD1BA
003CD168 64:FF30 push dword ptr fs:
003CD16B 64:8920 mov dword ptr fs:, esp
003CD16E 8B45 0C mov eax, dword ptr
003CD171 E8 1EFDFFFF call 003CCE94 跟进
003CCEB1 55 push ebp
003CCEB2 68 29CF3C00 push 003CCF29
003CCEB7 64:FF30 push dword ptr fs:
003CCEBA 64:8920 mov dword ptr fs:, esp
003CCEBD 8D45 F4 lea eax, dword ptr
003CCEC0 E8 A373FBFF call 00384268
003CCEC5 8B45 FC mov eax, dword ptr
003CCEC8 E8 5B76FBFF call 00384528
003CCECD 8BF0 mov esi, eax
003CCECF 85F6 test esi, esi
003CCED1 7E 26 jle short 003CCEF9
003CCED3 BB 01000000 mov ebx, 1
003CCED8 8D45 F0 lea eax, dword ptr
003CCEDB 8B55 FC mov edx, dword ptr
003CCEDE 0FB6541A FF movzx edx, byte ptr ; 取code各位的ASCII码值
003CCEE3 03D3 add edx, ebx ; 同循环次数相加
003CCEE5 E8 6675FBFF call 00384450
003CCEEA 8B55 F0 mov edx, dword ptr
003CCEED 8D45 F4 lea eax, dword ptr
003CCEF0 E8 3B76FBFF call 00384530 ; 将和作为ASCII码值转换为对应的字符
003CCEF5 43 inc ebx
003CCEF6 4E dec esi
003CCEF7^ 75 DF jnz short 003CCED8
003CCEF9 8D55 F8 lea edx, dword ptr
003CCEFC 8B45 F4 mov eax, dword ptr
003CCEFF E8 A05FFBFF call 00382EA4 循环取上面生成字符串的各位,如果当位不是数字就停止循环。
003CCF04 8BD8 mov ebx, eax
003CCF06 33C0 xor eax, eax
003CCF08 5A pop edx
003CCF09 59 pop ecx
003CCF0A 59 pop ecx
003CCF0B 64:8910 mov dword ptr fs:, edx
003CCF0E 68 30CF3C00 push 003CCF30
003CCF13 8D45 F0 lea eax, dword ptr
003CCF16 BA 02000000 mov edx, 2
003CCF1B E8 6C73FBFF call 0038428C
003CCF20 8D45 FC lea eax, dword ptr
003CCF23 E8 4073FBFF call 00384268
003CCF28 C3 retn
上面的call主要是对code进行了变换,接着往下看。
003CD176 50 push eax
003CD177 8B45 08 mov eax, dword ptr
003CD17A E8 89FEFFFF call 003CD008 跟进
003CD008 55 push ebp
003CD009 8BEC mov ebp, esp
003CD00B 51 push ecx
003CD00C 53 push ebx
003CD00D 8945 FC mov dword ptr , eax
003CD010 8B45 FC mov eax, dword ptr
003CD013 E8 0077FBFF call 00384718
003CD018 33C0 xor eax, eax
003CD01A 55 push ebp
003CD01B 68 63D03C00 push 003CD063
003CD020 64:FF30 push dword ptr fs:
003CD023 64:8920 mov dword ptr fs:, esp
003CD026 33DB xor ebx, ebx
003CD028 8B45 FC mov eax, dword ptr
003CD02B E8 F874FBFF call 00384528
003CD030 85C0 test eax, eax
003CD032 7E 19 jle short 003CD04D
003CD034 BA 01000000 mov edx, 1
003CD039 8B4D FC mov ecx, dword ptr
003CD03C 0FB64C11 FF movzx ecx, byte ptr ; 取name各位的ASCII码值
003CD041 03D9 add ebx, ecx ; 同ebx相加,ebx初始为0
003CD043 81F3 05FA0B00 xor ebx, 0BFA05 ; 和同0xBFA05异或
003CD049 42 inc edx
003CD04A 48 dec eax
003CD04B^ 75 EC jnz short 003CD039
003CD04D 33C0 xor eax, eax
003CD04F 5A pop edx
003CD050 59 pop ecx
003CD051 59 pop ecx
003CD052 64:8910 mov dword ptr fs:, edx
003CD055 68 6AD03C00 push 003CD06A
003CD05A 8D45 FC lea eax, dword ptr
003CD05D E8 0672FBFF call 00384268
003CD062 C3 retn
003CD063^ E9 546BFBFF jmp 00383BBC
003CD068^ EB F0 jmp short 003CD05A
003CD06A 8BC3 mov eax, ebx
003CD06C 5B pop ebx
003CD06D 59 pop ecx
003CD06E 5D pop ebp
003CD06F C3 retn
上面的call对name进行了变换,产生了一个数,我们记为sum。
003CD17F E8 B4FDFFFF call 003CCF38 跟进
003CCF38 55 push ebp
003CCF39 8BEC mov ebp, esp
003CCF3B 83C4 F8 add esp, -8
003CCF3E 8945 FC mov dword ptr , eax
003CCF41 53 push ebx
003CCF42 8B5D FC mov ebx, dword ptr
003CCF45 B8 79954101 mov eax, 1419579 ; tempnum = 0x1419579
003CCF4A 89C2 mov edx, eax
003CCF4C C1E0 03 shl eax, 3
003CCF4F 01D0 add eax, edx ; tempnum * 9
003CCF51 01C3 add ebx, eax ; 同sum相加
003CCF53 81C3 44A21300 add ebx, 13A244 ; 再加上0x13A244
003CCF59 81F3 C3E85900 xor ebx, 59E8C3 ; 同0x59E8C3异或
003CCF5F 81F3 2173C400 xor ebx, 0C47321 ; 同0xC47321异或,写注册机的时候我们可以先把两个常数先异或了
003CCF65 895D F8 mov dword ptr , ebx
003CCF68 5B pop ebx
003CCF69 8B45 F8 mov eax, dword ptr
003CCF6C 59 pop ecx
003CCF6D 59 pop ecx
003CCF6E 5D pop ebp
003CCF6F C3 retn
上面对之前生成的sum又进行了变换。
003CD184 5A pop edx
003CD185 E8 E6FDFFFF call 003CCF70 比较call,逐位比较
到这里我们总结一下这个cm的算法:
1.首先将code各位的ASCII码值加上循环次数,产生一个新的字符串。然后依次验证各位,遇到不是数字的就停止循环。以此产生一个数字,记为num1。
2.对name各位的ASCII码值进行一系列的异或和加法变换,产生一个新的数字,记为num2。
3.如果num1 = num2,则注册成功。
那么我们写注册机的思路也很简单了。先算出num2,然后将num2的各位ASCII码值减去循环次数,再变换为新的字符就行了。下面给出注册机源代码(VS2005+windows sp2下编译通过):void CpediyDlg::OnBnClickedButton1()
{
CString username;
CString tempstr1;
CString tempstr2;
CString sn;
int i,j, k ,length, tmpnum1, tmpnum2, tmpnum3 , sum = 0;
char c;
if (GetDlgItemText(IDC_EDIT1, username) == 0)
{
MessageBox("请输入用户名!");
}
else
{
length = username.GetLength();
tmpnum2 = 0x1419579;
for (i = 0;i<length;i++)
{
tmpnum1 = username;
sum = sum + tmpnum1;
sum = sum ^ 0xBFA05;
}
tmpnum2 = tmpnum2 * 9;
sum = (sum + tmpnum2 + 0x13A244) ^ 0x9D9BE2;
tempstr1.Format("%d", sum);
j = tempstr1.GetLength();
for (k = 1;k <= j;k++)
{
tmpnum3 = tempstr1 - k;
char c = (char)tmpnum3;
tempstr2.Format("%c", c);
sn = sn + tempstr2;
}
SetDlgItemText(IDC_EDIT2,sn);
}
}------------------------------------------------------------------------
【破解总结】总的来说这个cm比较简单,比较的方式为逐位比较。
------------------------------------------------------------------------
【版权声明】本文原创于52pojie技术论坛, 转载请注明作者并保持文章的完整, 谢谢!
crackme:
支持原创! 谢谢了,学习下 学习,学习 给你顶一下 看看怎么样啊
页:
[1]