Writing your own key generator
WinZip 7.0
We downloaded a copy of WinZip 7.0 from the following Url. http://www.oldversion.com/download.php?idlong=2588aa9d564e0bdc60dacd33576800c7. This is a site that keeps older versions of software for people like us who need to run a exploit on a certain version only. After installing winzip it keeps nagging us to pay for it. Good product and we recommend you should pay at least once for using it. We will now show you how to write a program that generates a key that winzip accepts as a valid key.
There is a gentleman some where on the net that placed code that does the above magic. He goes by the name Lord Soth. He wrote the original code that displays a dialog box, we have simplified his code and explained it. No changes at all to what he has done. In this case we know his name but in lots of cases we have found great code on the net and do not know who has placed it there.
a.cpp
#include <windows.h>
#include "stdio.h"
#include "string.h"
char username[255]="", serial[255]="",*upper;
int i, j, length, con=4129,result1, current_letter, tmp_letter,result2;
int main(int argc, char *argv[])
{
strcpy(username,argv[1]);
length = strlen( username );
for (i=0 ; i < length ; i++)
{
current_letter = username[i];
current_letter = current_letter << 8;
result1 += username[i]*i;
for (j=0 ; j < 8 ; j++)
{
tmp_letter = current_letter;
tmp_letter = tmp_letter ^ result2;
if ( (LOWORD(tmp_letter) & 32768) )
{
result2 += result2;
result2 = result2 ^ con;
current_letter *= 2;
}
else
{
current_letter *= 2;
result2 *= 2;
}
}
}
result2 += 99;
printf("%x %x\n",result2,result1);
sprintf ( serial, "%x%4x", LOWORD(result2), result1);
for (i=0 ; i < strlen(serial) ; i++)
if (serial[i] == ' ')
serial[i] = '0';
upper = _strupr (serial);
printf(upper);
}
As usual we have all our variables global and will pass the user name as a command line parameter to our program. The key generated depends upon the name of the user that we type into winzip when we register ourselves. We first use the strcpy function to copy the string in argv[1] to the array username. We then use the function strlen to give us the length of the string. Our user name is Vijay Mukhi so strlen returns us 11 which we store in the variable length.
We then use a for loop to iterate the value of I from 0 to 10, using I as an array offset into the username array, Thus the variable current_letter becomes each individual character of our user name. The ASCII value of V is 86. We then left shift this value eight times effectively multiplying 86 by 256 giving us a value 22016. We do this for every character we have typed as the user name.
We then take each and every character that we have typed and multiply it by the position that it occupies in the string. Thus V get multiplied by 0, I by 1 and j by 2. We store a running total of all this in the variable result2. This gives us values 0, 105, 317, 608 etc. Remember this variable result2 contains running totals. The last value it contains is 5375.
We enter one last for loop where j goes from 0 to 7 for a total of 8. We set the value of variable tmp_letter to current_letter which was the value V multiplied by 256 or 22016. We then bit wise or this value with what is stored in variable result2 which as of now is 0. Bitwise oring makes a bit 1 if any of the bits is 1, otherwise it keeps things the same.
Now we come across an if else statement. The macro LOWORD simply gives us the first 16 bits of a number. Thus this macro will gives us value less that 65536. Any value above this will be truncated. The first value of tmp_letter is 22016 and LOWRD gives us the same value back. The third value is 88064 and LOWORD gives us 18465.
In the if statement we bit wise and with 32768 which means that the 15th bit is 1 and the remaining bits are 0. Thus any value larger than 32768 will make the if statement true, a value smaller will give us false. Thus the first value is 22016 and the else gets called. Here we multiply result2 by 2 and current_letter which is 22016 doubles and becomes 44032 which is now used in the start of the for.
In the second iteration of the loop the value of tmp_letter becomes larger than 32768 and the if is called. Here we simply add the values of result2 and not multiply it, we then bitwise or it with a constant con whose value is 4129. We like in the else multiply current_letter by 2.
At the end of the two for loops the value of result2 is 736826306. We then add 99 to the value of result2. The final value of result2 is 2beb1425 and result1 is 14ff. We then create a number taking the lower 16 bits of result2 1425 and result1 14ff and get 142514ff the key. We then introduce a check that does not apply in our case, if we come across a space or 32 we replace it with a 0. Finally we convert the entire string into upper case, the two small ff’s become all caps.
We then install the copy of winzip 7.0 and click on help enter registration info and write Vijay Mukhi and the above number. It works as advertised. Program name KeyWinzip70.exe and keywinzip70.cpp
Mighty Fax 2.9
We went to a site http://www.rkssoftware.com/mfntv29z.exe to download the above file that we installed. We then wrote a key generator for this program.
When we start the program it gives us 30 day trial and also asks us for a serial number. We click on the button serial number instead of Continue and write Vijay Mukhi as the name and the serial number as RKS-5379914. When we click on OK it gives us a message box saying number accepted. Lets now write a program to generate such a serial number.
a.cpp
#include <windows.h>
#include "generic.h"
#include "resource.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
char username[255]="", serial[255]="RKS-";
int seed,i;
DWORD sn;
int main(int argc, char *argv[])
{
srand( (unsigned) time(NULL));
strcpy(username, argv[1]);
_strupr( username);
seed = rand();
seed /= 8192;
if (seed == 0)
seed = 0x1b54;
else if (seed == 1)
seed = 0x1b1f;
else if (seed == 2)
seed = 0x1771;
else
seed = 0x17d9;
for ( i=0 ; i < lstrlen( username) ; i++)
{
if ( username[i] != ' ')
{
sn += seed * username[i];
sn--;
}
}
sprintf( username, "%d", sn);
lstrcat( serial, username);
printf("%s\n",serial);
}
The srand function initializes the random number generator with the current time as the seed. Time gives us the current time. If we use 1 as a parameter to srand it reinitializes the random number generator. Any other value set it to some random starting point. As before we copy the username in argv[1] to the global array username and make the entire string uppercase by using the function strupr.
The rand function returns a random number from 0 to RAND_MAX which is defined as 32767. In our case we first got a value 6281 and then 6291. We then divide this value of seed by 8192 and in our case we get 0 as the answer.
Depending upon the value after dividing seed we give it a new value, there are four different value it can take. For us the value is the first 0x1bf4. Like before we pick up each and every character of our user name and simply multiply it by the seed we just chose. We store this running total in the variable sn. We also reduce sn by 1 in the loop. When we get out of the loop the value of sn is the key and w concatenate it with the words RKS.
Program name keymightyfax20.exe and keymightyfax29.cpp