MASTERING THE ART PART III by ArthaXerXès - 29th June 2000 - |
version 1.0 |
I finally managed to find the time to write this new essay !
At first I wanted to write an essay about Windows 2000 serial verification procedure, but the time has not come. What we shall study today is how to make a key generator and we shall take advantage of the situation to study Visual Basic programs (here a Visual Basic 3 one).
I am very disapointed. None of you did notice the intentional mistake in the previous one? If you followed exactly my steps, you would have indeed removed the message box when changing the file extension, but as well removing the message box for most shell messages !
My main goal was to show you, through experience, that you should always test thorougly your work. Actually, if you want to only remove the check for this special case (id est when changing the file extension) you need to dig a little bit deeper, but it is really not hard if you are careful.
The other purpose of this mistake was to show you that you must never accept something as the truth without checking. I can be mistaken, such as you, keep this in mind : this is very important. In addition, you may have to deal with information that is intentionally wrong to mislead you.
The "hacker" state of mind is mainly about seeking Knowledge, generally speaking, the difficulty being to determine what is true and what is not. You have to question everything, even other hackers (of course, you should never be disrespectful).
Should you wish to contact me, mail to xerxes@altern.org. You can get my public PGP key at http://www.altern.org/xerxes/ which is the URL of my modest web site. Since I am French, you can mail me either in French or in English. Use the language you prefer. You may also contact me through +Fravia's message board or mine.
Please, avoid useless mails, i.e. ask only clever questions ! On the other hand, I welcome critics and suggestions, as well as corrections.
I use neither ICQ nor IRC, if you meet someone claiming to be ArthaXerXès using these media, it is a lie.
I will assume that you have at least red all the previous essays, if you did not, I really encourage you to do so.
A keygenerator is a program that generates a key for a given program. As you certainly know, most programs ask to become fully functionnal (or sometimes to install) a serial number (that we shall call the key).
This key is generally dependent of a registration name, and sometimes you have several keys. In WinHex (see part I), it asked for two "registration numbers". When you register, the author gives you these numbers so as to unlock the program.
In the essay we attacked the program in a more simple way, we simply modified it so that it believes it has been registered. It always work, id est if a program asks you for a serial number, instead of finding out how it is generated you can hack the program so that it accepts any key or that it believes it has already been registered.
Moreover, it is generally easier to do so, since in order to find how the key is generated, you need to reverse the comparaison algorithm. Sometimes it is a simple compare (most of the cases), and you therefore have to merely look in memory for the correct value, but it can be much more complex.
Indeed, sometimes complex mathematic computation is performed on the serial and the name to see if they are correct. This prevents you from easily guessing the correct values (but does not make it impossible).
Of course, most of the time the serial you found is only valid for the name you entered (if it was a typical name/key registration scheme). This is the purpose of a key generator, allowing anyone to use the name he wishes. This is also more challenging, for you, the reverser.
But you may ask, why should I create a key generator when if patching is easier ?
Here are some reasons :
Softice is obviously required, but you will also need DoDi's VB Discompiler (this is for Visual Basic,you can find it on http://protools.cjb.net/), a text editor (I like UltraEdit, http://www.ultraedit.com/), a C++ compiler (I use Borland Builder C++ 5, but the GNU C++ should do it) and of course the target program : Visual Help Pro 4 (the time limited demo can be downloaded at : http://www.winwareinc.com/).
The first thing you would try is to trace the program with Softice after the message box. But after little tracing, you will find yourself in a DLL called vbrun300.dll. This is the visual basic runtime.
Visual Basic is not a "real compiler", a visual basic executable is only a sequence of calls to vbrun300.dll functions. This is why it is such a bad language (and I am not even talking about the nature of the language itself which is also very bad).
This prevents us from either decompiling the program with IDA or making efficient trace with Softice. What we could do is to intercept the call to the visual basic function that compares strings, but this would give us only one serial (furthermore it would only work if the program compares the serial we gave with the valid one).
Fortunately, there is a VB3 discompiler which will produce Visual Basic code (and not assembly code). This is possible because a lot of redundant information is present in the executable.
Sometimes these information have been removed (by a protector), but there is a program called"VB3 Deprotector" that deprotects VB3 programs (as you may have guessed ;-).
Load the file vh.exe in the discompiler, various error messages will be shown. You may discard them, our goal is not to obtain recompilable source code (which we could). I suggest you to save all the files in a seperate directory.
Oncedone, load the file "register.bas" into your editor, the function ok_button_Click is the
one we are looking for.
Const mc0030 = 400 ' &H190%
. . .
If Trim( Text1 . Text) <> "" And Trim( Text2 . Text) <> "" Then
l0032$ = "vh" + Trim( Str ( mc0030 + 173 +
Asc ( Left$ ( LCase ( Trim( Text1 . Text )), 1)))) + "-" +
Trim( Str ( mc0030)) + "-" +
Trim( Str ( Asc ( Left$ ( LCase ( Trim( Text1 . Text )), 1)) * 4))
// the correct s e r i a l has been generated
If l0032$ = Trim( LCase ( Text2 . Text ))
Then l0034 = True Else l0034 = False
// we compare with the given one
Pretty easy, is not it ? Now we need to understand how the serial is generated.
Note that the serial always start with "vh". Run the program and provide a bogus name/serial pair. Put a breakpoint on MessageBoxA (bpx MessageBoxA) and search for "vh" in memory (s 0 l ffffffff "vh"). You should find the serial we are looking for.
For example if you entered "Registered user", the serial is "vh687-400-456". Well, we have one serial and the routine, it should now be very easy to understand it (even if, like me, you do not know Visual Basic at all).
We know the form is always "vhXXX-XXX-XXX", we also know that the center number is always 400 (this is the constant mc0030).
The left number is equal to the constant plus the ASCII value of the first character of the string (lower case) plus 173. In our example, the first character is `R', the ASCII value of `r' is 114, 400 + 114 + 173 = 687, which is what we found in memory.
The right number is equal to the ASCII value of the first character of the string (still lower case) multiplied by 4. In our case, the value is 114 * 4 = 456, and again this is what we found in memory.
As you can see it is a very simple algorithm, but it is better to have a correct name/key pair to check.
We reversed, now we forward !
Here is a sample routine in C++, directly taken from my own key generator :
AnsiString vh_keygen : : generate ( AnsiString name)
{
const int vh _const = 400;
AnsiString name_bis ;
AnsiString c u r _ s e r i a l ;
name_bis = name. LowerCase ();
c u r _ s e r i a l = "vh" ;
c u r _ s e r i a l += (vh _const + 173 + name_bis [ 1 ] ) ;
c u r _ s e r i a l += '-';
c u r _ s e r i a l += vh _const ;
c u r _ s e r i a l += '-';
c u r _ s e r i a l += (name_bis [1] * 4);
return c u r _ s e r i a l ;
}
Note : the AnsiString object is specific to BC++. Use mere strings if you use another compiler.
If you are curious, I created a class keygen with an abstract method, and implemented the routine in a class that inherits it called vh_keygen. This enables me to easily adapt the key generator.
Of couse what we studied here is a simple case, but the method remains identical for tougher case : locatethe algorithm, reverse it and reengineer it.
However, you must understand that other programs (non-vb ones) will have their serial verification routine in assembly, which is harder to cope with. In a future essay, we shall study a real program.
Regarding Visual Basic programs, what we saw here is valid for VB3. For other versions, you may wish to use an API monitor such as BoundChecker. Razzia's essay is a recommended reading if you are interested in VB.
The next essay will be about Windows 2000 serial verification procedure. I shall show you how to
bypass the installation check to install the system without any valid serial at all. I know this
hack sounds very elite (How to reverse a system installer ? How to modify it ?), but as you will see
it is not.
Made with LATEX2e on Thursday 29th June 2000. Version 1.0