Olly V1.10 Step 2 Family KeyLogger (V2.80)
Open up Family Keylogger and it adds an icon to the task bar. When you right click the icon there is the option to register it. Clicking it reveals we need to enter a serial. We will crack the program so we don't need to enter any serial.
Close the program and open it up in olly. Hit F9 to run it then get to the box where we enter the serial. Enter any serial you want but don't press OK just yet. In olly place a breakpoint on the function GetDlgItemTextA, here is one way to do it. Hit CTRL+G to open up the go to expresion box and enter the name GetDlgItemTextA and hit enter. We land at the start of GetDlgItemTextA:
77D47FEC 6A 0C PUSH 0C
For you the address may not be 77D47FEC depending on your version of windows. Hit F2 to place a breakpoint on this address then in Family Keylogger press OK. Olly breaks at GetDlgItemTextA. Now lets see if this call to GetDlgItemTextA is actually getting the serial. In the stack window select the buffer argument, right click it and chose follow in dump. Now press ALT+F9 to tell olly that we want to run the program untill we are no longer in a system dll (which will mean we have returned from GetDlgItemTextA). Notice that the serial apears in the memory dump. Now take a look at the code that follows the call to DlgItemTextA, you should be able to tell that the serial is saved to a file and then there is the serial check function.
0040350B E8 0EEAFFFF CALL ctfmon.00401F1E
00403510 0FBEC0 MOVSX EAX,AL
00403513 85C0 TEST EAX,EAX
00403515 75 28 JNZ SHORT ctfmon.0040353F
00403517 6A 00 PUSH 0 ; /Style = MB_OK|MB_APPLMODAL
00403519 8B0D 08514000 MOV ECX,DWORD PTR DS:[405108] ; |ctfmon.00405160
0040351F 51 PUSH ECX ; |Title => "FamilyKeyLogger"
00403520 8B15 54514000 MOV EDX,DWORD PTR DS:[405154] ; |ctfmon.00405480
00403526 52 PUSH EDX ; |Text => "Thank you for registration!"
00403527 8B45 08 MOV EAX,DWORD PTR SS:[EBP+8] ; |
0040352A 50 PUSH EAX ; |hOwner
0040352B FF15 88114000 CALL DWORD PTR DS:[<&USER32.MessageBoxA>>; \MessageBoxA
From this peice of code we can see that if the function at 00401F1E returns 0 then the program shows the message "Thank you for registration!". If we noped out the jump at 00403515 then we could make it show that message no matter what serial we entered. But wait! Why is the serial saved to a file? So that it can be loaded from the file at program startup and checked to see if the program is registered. The program isn't going to show the "Thank you for registration!" message every time we start it so the serial check function is probably being called from some other place as well and it could be checked more then once. The point is it is better to patch the serial check function itself so that it will always return 0. With many programs with a protection like this is would be enough to set eax to 0 (or whatever the particular program expected) and return from the function but with this program there is one more thing we need to do. My first attempt at a crack made the serial check function (00401F1E) always return 0 in eax. This apeared to work untill I set my date foreward by a year and started the program and it told me I handn't registered.
As well as putting 0 into eax the serial check function must do something else to indicate that a correct serial is stored in the file. Hit enter on the call to 00401F1E, we land here:
00401F1E 55 PUSH EBP
Hit CTRL+R to see where abouts this function is called from in the program
References in ctfmon:.text to 00401F1E
Address Disassembly Comment
00401807 CALL ctfmon.00401F1E
00401CEC CALL ctfmon.00401F1E
00401F1E PUSH EBP (Initial CPU selection)
00403334 CALL ctfmon.00401F1E
0040350B CALL ctfmon.00401F1E
There are 4 calls to this function. Just after some of these calls there should be a test to see if eax (actually al) contains 0 and then some additional variable(s) that the serial check function set. We might as well start with the first call at 00401807, double click that line.
00401807 E8 12070000 CALL ctfmon.00401F1E
0040180C 0FBEC8 MOVSX ECX,AL
0040180F 85C9 TEST ECX,ECX
00401811 75 09 JNZ SHORT ctfmon.0040181C
00401813 833D F8544000 >CMP DWORD PTR DS:[4054F8],0
hmm a check to see if al contains 0 as we expected and now a check to see if the DWORD at 4054F8 is 0. select the line at 00401813 and right click it. Select Find references to->Address constant.
00401F28 MOV DWORD PTR DS:[4054F8],0
Here is where the DWORD at 4054F8 is set to 0 and it is near the start of the serial check function. So we want our serial check function to return 0 and make sure DWORD at 4054F8 is 0. In this program they are using 0 for correct and 1 for incorrect wich seams to be the oposite to what you'd expect. Go to code location 00401F32 which is just after the DWORD at 4054F8 is set to 0, this is the point that it should be safe to exit this function. we need to set al to 0 and return from the function but we can't just place a retn into the function because the stack would be messed up and the retn would cause the program flow to jump to whatever value is on the stack which would most certainly result in a crash. Wouldn't it be nice if there was allready a peice of code in this function that we could use that would set al to 0 and exit the function properly? well there is at the very end of the function.
0040222F |> 32C0 XOR AL,AL
00402231 |> 5E POP ESI
00402232 |. 8BE5 MOV ESP,EBP
00402234 |. 5D POP EBP
At code location 00401F32 hit space bar to bring up the assembler and type JMP 0040222F. That is the only change we need to make to crack this program :). If the serial check function set some other variables then we would have to locate those as well. All we need to do now is right click and chose copy to executable->all modifications.
Nilrem
Enforcer
ferrari
Pompeyfan
MAdMaN H3rLcUl3S
EJ12N
Kruger