HappyTown的第21个CrackMe分析
- 首先感谢HappyTown为我们带来这么好的CrackMe。
详细过程
首先感谢HappyTown为我们带来这么好的CrackMe。
用到了OpenSSL库。
一、基本情况分析:
1. 用PEiD分析,发现未加壳;
2. 用Kanal查看得知使用了MD5,用IDA加载openssl的sig文件后,导出MAP文件;
3. 随便输入信息,发现未有出错提示;
4.但用W32DASM发现了Congratulations。它的前面有个je的跳转,再往前有个call00401130在00401081处。
二、正式开工:
1. OD载入,用bp 401081下断点,并加载刚才生成的MAP文件;
2. 运行程序,输入假码:
name: HorstStein
sn:9876543210ABCDEF (为什么是16个字符,请看下面)
3. 点击Check被断,进入00401130:
00401130 />sub esp, 3CC
00401136 >push ebx
00401137 >push ebp
00401138 >push esi
00401139 >push edi
0040113A >mov ecx, 31
0040113F >xor eax, eax
00401141 >lea edi, [esp+165]
00401148 >mov byte ptr [esp+164], 0
00401150 >rep stos dword ptr es:[edi]
00401152 >stos word ptr es:[edi]
00401154 >stos byte ptr es:[edi]
00401155 >mov ecx, 31
0040115A >xor eax, eax
0040115C >lea edi, [esp+41]
00401160 >mov byte ptr [esp+40], 0
00401165 >rep stos dword ptr es:[edi]
00401167 >stos word ptr es:[edi]
00401169 >stos byte ptr es:[edi]
0040116A >mov esi, [esp+3E0]
00401171 >xor eax, eax
00401173 >mov edi, [<&USER32.GetDlgItemTextA>];USER32.GetDlgItemTextA
00401179 >mov [esp+29], eax
0040117D >mov [esp+2D], eax
00401181 >xor ecx, ecx
00401183 >lea edx, [esp+164]
0040118A >mov [esp+31], eax
0040118E >mov [esp+21], ecx
00401192 >push 0C9 ; /Count = C9 (201.)
00401197 >push edx ; Buffer
00401198 >mov [esp+3D], ax ;
0040119D >mov ebx, 4 ;
004011A2 >mov [esp+2D], cx ;
004011A7 >push 3E8 ; ControlID = 3E8 (1000.)
004011AC >push esi ; hWnd
004011AD >mov byte ptr [esp+38], 0 ;
004011B2 >mov [esp+47], al ;
004011B6 >mov [esp+20], bl ; //密钥从[esp+20]开始;bl=04
004011BA >mov byte ptr [esp+21], 0B5 ;
004011BF >mov byte ptr [esp+22], 52 ;
004011C4 >mov byte ptr [esp+23], 6C ;
004011C9 >mov byte ptr [esp+24], 0DC ;
004011CE >mov byte ptr [esp+25], 6 ;
004011D3 >mov byte ptr [esp+26], 0C4 ;
004011D8 >mov byte ptr [esp+27], 0DF ;
004011DD >mov byte ptr [esp+28], 87 ;
004011E2 >mov byte ptr [esp+29], 0C2 ;
004011E7 >mov byte ptr [esp+2A], 0AA ;
004011EC >mov byte ptr [esp+2B], 75 ;
004011F1 >mov byte ptr [esp+2C], 0DE ;
004011F6 >mov byte ptr [esp+2D], 7 ;
004011FB >mov [esp+2E], bl ; bl=04
004011FF >mov byte ptr [esp+2F], 8 ; \\密钥到[esp+2F]结束,长度16
00401204 >mov [esp+30], al ;
00401208 >mov [esp+37], cl ;
0040120C >call edi ; \GetDlgItemTextA
0040120E >mov ebp, eax ; len(name)
00401210 >cmp ebp, ebx ; name长度不小于4
00401212 >jge short 00401221
00401214 >pop edi
00401215 >pop esi
00401216 >pop ebp
00401217 >xor eax, eax
00401219 >pop ebx
0040121A >add esp, 3CC
00401220 >retn
00401221 >lea eax, [esp+40]
00401225 >push 0C9
0040122A >push eax
0040122B >push 3E9
00401230 >push esi
00401231 >call edi ; 取输入的sn
00401233 >cmp eax, 10 ; 注册码长度必须为16
00401236 >je short 00401245
00401238 >pop edi
00401239 >pop esi
0040123A >pop ebp
0040123B >xor eax, eax
0040123D >pop ebx
0040123E >add esp, 3CC
00401244 >retn
00401245 >xor esi, esi
00401247 >/cmp dword ptr [4082E8], 1 ;//检查输入的序列号sn是否为16进制数,同时转化为小写
0040124E >jle short 00401265
00401250 >movsx ecx, byte ptr [esp+esi+40]
00401255 >push 80
0040125A >push ecx
0040125B >call <__isctype>
00401260 >add esp, 8
00401263 >jmp short 00401277
00401265 >movsx edx, byte ptr [esp+esi+40]
0040126A >mov eax, [4080DC]
0040126F >mov al, [eax+edx*2]
00401272 >and eax, 80
00401277 >test eax, eax
00401279 >je short 00401214
0040127B >movsx ecx, byte ptr [esp+esi+40]
00401280 >push ecx
00401281 >call <_tolower>
00401286 >add esp, 4
00401289 >mov [esp+esi+40], al
0040128D >inc esi
0040128E >cmp esi, 10
00401291 >\jl short 00401247 ; \\
00401293 >xor edi, edi
00401295 >lea esi, [esp+41]
00401299 >/cmp dword ptr [4082E8], 1 ; //把sn转化成对应的十六进制
004012A0 >jle short 004012B3
004012A2 >movsx edx, byte ptr [esi-1]
004012A6 >push 2
004012A8 >push edx
004012A9 >call <__isctype>
004012AE >add esp, 8
004012B1 >jmp short 004012C3
004012B3 >movsx eax, byte ptr [esi-1]
004012B7 >mov ecx, [4080DC] ; CrackMe_.004080E6
004012BD >mov al, [ecx+eax*2]
004012C0 >and eax, 2
004012C3 >mov bl, [esi-1]
004012C6 >test eax, eax
004012C8 >jnz short 004012CF
004012CA >sub bl, 30
004012CD >jmp short 004012D2
004012CF >sub bl, 57
004012D2 >cmp dword ptr [4082E8], 1
004012D9 >jle short 004012EB
004012DB >movsx edx, byte ptr [esi]
004012DE >push 2
004012E0 >push edx
004012E1 >call <__isctype>
004012E6 >add esp, 8
004012E9 >jmp short 004012FA
004012EB >movsx eax, byte ptr [esi]
004012EE >mov ecx, [4080DC] ; CrackMe_.004080E6
004012F4 >mov al, [ecx+eax*2]
004012F7 >and eax, 2
004012FA >test eax, eax
004012FC >mov al, [esi]
004012FE >jnz short 00401304
00401300 >sub al, 30
00401302 >jmp short 00401306
00401304 >sub al, 57
00401306 >shl bl, 4
00401309 >or bl, al
0040130B >add esi, 2
0040130E >mov [esp+edi+20], bl
00401312 >inc edi
00401313 >cmp edi, 8
00401316 >\jl short 00401299 ; \\
00401318 >lea edx, [esp+108]
0040131F >push edx
00401320 >call
//MD5_Init:
00401B80 >/>mov eax, [esp+4] ; MD5_Init
00401B84 >xor ecx, ecx
00401B86 >mov dword ptr [eax], 67452301 ; //MD5的4个常数
00401B8C >mov dword ptr [eax+4], EFCDAB89
00401B93 >mov dword ptr [eax+8], 98BADCFE
00401B9A >mov dword ptr [eax+C], 10325476 ; \\
00401BA1 >mov [eax+10], ecx
00401BA4 >mov [eax+14], ecx
00401BA7 >mov [eax+58], ecx
00401BAA >mov eax, 1
00401BAF \>retn
\\
00401325 >lea eax, [esp+168]
0040132C >push ebp ; len(name)
0040132D >lea ecx, [esp+110]
00401334 >push eax ; name
00401335 >push ecx
00401336 >call
0040133B >lea edx, [esp+118]
00401342 >lea eax, [esp+38]
00401346 >push edx
00401347 >push eax ; //在这里先d eax
00401348 >call
0040134D >lea ecx, [esp+244];\\看内存区,MD5(HorstStein)=82E0134547E6AF1C4D677811201710E7
00401354 >lea edx, [esp+28]
00401358 >push ecx;由openssl库idea.h头文件可知此乃IDEA_KEY_SCHEDULE结构,即存放子密钥的地方
00401359 >push edx ; 用于IDEA的key:04 B5 52 6C...向上翻翻看:D
0040135A >call <_idea_set_encrypt_key> ; 设置IDEA加密密钥
0040135F >lea eax, [esp+324]
00401366 >lea ecx, [esp+24C]
0040136D >push eax
0040136E >push ecx
0040136F >call ; 设置IDEA解密密钥
00401374 >lea edx, [esp+32C]
0040137B >lea eax, [esp+60]
0040137F >push edx
00401380 >lea ecx, [esp+4C]
00401384 >push eax
00401385 >push ecx ; sn
00401386 >call <_idea_ecb_encrypt> ; 解密sn(ecb模式)
0040138B >add esp, 34
0040138E >mov ecx, 2
00401393 >lea edi, [esp+28]
00401397 >lea esi, [esp+38]
0040139B >xor edx, edx
0040139D >repe cmps dword ptr es:[edi], dword ptr [esi]
0040139F >pop edi
004013A0 >mov eax, edx
004013A2 >pop esi
004013A3 >pop ebp
004013A4 >sete al
004013A7 >pop ebx
004013A8 >add esp, 3CC
004013AE \>retn
三、其验证算法:
1. h=MD5(name);
2. x=IDEA(sn,Decrypt);
3. 判断h=x否,相等则成功,不等则失败
两组可用的注册码:
name:HorstStein
sn:03CDCA61C437218C
name:pediy
sn:6A46FF71FCCAAC76
四、注册机算法及其代码:
1. 算法:IDEA(MD5(name),Encrypt)。
2. 代码(用到了OpenSSL库):
int main()
int i;
int nLenName; //name长度
char szName[150] = 0; //存放name
MD5_CTX md5;
unsigned char MD5Name16= 0; //存放MD5(szName)的消息摘要
unsigned char cSerial_test8= 0; //临时存放注册码
unsigned char outEn[8]; //存放IDEA的输出
unsigned char szBuffer[150]=0; //存放注册码
IDEA_KEY_SCHEDULE key; //存放IDEA加密子密钥
unsigned char k16= 0x04,0xB5,0x52,0x6C,0xDC,0x06,0xC4,0xDF,
0x87,0xC2,0xAA,0x75,0xDE,0x07,0x04,0x08;//IDEA密钥
printf("Enter your name:");
scanf("%s",szName);
//MD5(szName)
MD5_Init( &md5);
MD5_Update( &md5, szName, nLenName);
MD5_Final( MD5Name, &md5);
//设置IDEA加密密钥
idea_set_encrypt_key(k,&key);
for (i=0; i<8; i++)
cSerial_test[i] = MD5Name[i];
//加密MD5(name)
idea_ecb_encrypt(cSerial_test,outEn,&key);
for (i=0; i<8; i++)
wsprintf(&szBuffer[i*2], "%02X", *(byte*)(outEn+i));
printf("\nSN:%s\n",szBuffer);
return 0;
经验总结
这个CrackMe的验证方式和很多使用RSA的CrackMe的验证方式类似,所以,值得我等菜鸟一学。
版权声明:
本文原创于看雪技术论坛, 转载请注明作者并保持文章的完整, 谢谢!
-
TAGS:
- 作者:管理员 时间:2009-6-21 来源:网络 人气: