1、汇编级程序
2、OD载入
搜索字符串,定位“Good work!”对话框,查找参考。
00401241 . 3BC3 cmp eax,ebx
00401243 . 74 07 je XCruehead.0040124C
00401245 . E8 18010000 call Cruehead.00401362 ; No luck
0040124A .^ EB 9A jmp XCruehead.004011E6
0040124C > E8 FC000000 call Cruehead.0040134D ; Good work
00401251 .^ EB 93 jmp XCruehead.004011E6
直接条件是判断 eax == ebx;
eax, ebx 分别来至于:
00401228 . 68 8E214000 push Cruehead.0040218E ; Name
0040122D . E8 4C010000 call Cruehead.0040137E ; 返回eax
00401232 . 50 push eax
00401233 . 68 7E214000 push Cruehead.0040217E ; Serial
00401238 . E8 9B010000 call Cruehead.004013D8 ; 返回ebx
0040123D . 83C4 04 add esp,0x4
00401240 . 58 pop eax
00401241 . 3BC3 cmp eax,ebx
call 0040137E(Name):
0040137E /$ 8B7424 04 mov esi,dword ptr ss:[esp+0x4]
00401382 |. 56 push esi
00401383 |> 8A06 /mov al,byte ptr ds:[esi]
00401385 |. 84C0 |test al,al
00401387 |. 74 13 |je XCruehead.0040139C
00401389 |. 3C 41 |cmp al,0x41 ; 'A'
0040138B |. 72 1F |jb XCruehead.004013AC ; ord(Name[i]) < 'A' 跳向失败
0040138D |. 3C 5A |cmp al,0x5A ; 'Z'
0040138F |. 73 03 |jnb XCruehead.00401394 ; ord(Name[i]) > 'Z' -> Name[i] -= 0x20 即小写转换成大写
00401391 |. 46 |inc esi
00401392 |.^ EB EF |jmp XCruehead.00401383
00401394 |> E8 39000000 |call Cruehead.004013D2
00401399 |. 46 |inc esi
0040139A |.^ EB E7 \jmp XCruehead.00401383
0040139C |> 5E pop esi
0040139D |. E8 20000000 call Cruehead.004013C2 ; 求和 sum(Name[i])
004013A2 |. 81F7 78560000 xor edi,0x5678
004013A8 |. 8BC7 mov eax,edi
004013AA |. EB 15 jmp XCruehead.004013C1
004013AC |> 5E pop esi
004013AD |. 6A 30 push 0x30 ; /Style = MB_OK|MB_ICONEXCLAMATION|MB_APPLMODAL
004013AF |. 68 60214000 push Cruehead.00402160 ; |No luck!
004013B4 |. 68 69214000 push Cruehead.00402169 ; |No luck there, mate!
004013B9 |. FF75 08 push [arg.1] ; |hOwner
004013BC |. E8 79000000 call <jmp.&USER32.MessageBoxA> ; \MessageBoxA
004013C1 \> C3 retn
原型:
int call_0040137E(char *Name){
int sum = 0;
for(int i = 0; Name[i] != 0; i++){
if(Name[i] < 'A'){
MessageBox("No luck!");
return 0;
}else if(Name[i] > 'Z'){
Name[i] -= 0x20;
}
sum += Name[i];
}
return sum ^ 0x5678;
}
Name只能是字母。
call 004013D8(Serial):
004013D8 /$ 33C0 xor eax,eax
004013DA |. 33FF xor edi,edi
004013DC |. 33DB xor ebx,ebx
004013DE |. 8B7424 04 mov esi,dword ptr ss:[esp+0x4]
004013E2 |> B0 0A /mov al,0xA
004013E4 |. 8A1E |mov bl,byte ptr ds:[esi]
004013E6 |. 84DB |test bl,bl
004013E8 |. 74 0B |je XCruehead.004013F5
004013EA |. 80EB 30 |sub bl,0x30 ; int(Serial[i])
004013ED |. 0FAFF8 |imul edi,eax
004013F0 |. 03FB |add edi,ebx ; sum += sum * 0x0A + Serial[i]
004013F2 |. 46 |inc esi
004013F3 |.^ EB ED \jmp XCruehead.004013E2
004013F5 |> 81F7 34120000 xor edi,0x1234
004013FB |. 8BDF mov ebx,edi
004013FD \. C3 retn
原型
int call_004013D8(char *Serial){
int al = 0x0A, ret = 0;
for(int i = 0; Serial[i] != 0; i++){
Serial[i] -= 0x30;
ret *= al;
ret += Serial[i];
}
return ret ^ 0x1234;
}
就是把字符串转为整形
3、注册机
>>> def keygen(Serial):
Serial.upper()
eax = sum([ord(i) for i in Serial]) ^ 0x5678
return eax ^ 0x1234
>>>
>>> keygen('ABC')
17546