views:

74

answers:

4

Throughout my days as a PHP Programmer and a beginner at C# programming I've always wondered of the best way to generate unique serials such as how Microsoft Office and Microsoft operating systems do.

Does anyone have a good guide to how to handle this, Like what are the important factors in generating the unique serial, prevent duplicates etc. small example on how to create / verify them.

Here is the RFC im tlaking about: http://tools.ietf.org/html/rfc1982

Any advice / guides / samples are appreciated :)

Regards

A: 

I'm not absolutely sure what you want, but there is http://www.php.net/manual/en/function.uniqid.php which creates Unique Identifiers.

If you're more interested in how they are created, I'd advice you to take a look at the PHP source to see how uniqid is implemented.

halfdan
Im talking in regards to http://tools.ietf.org/html/rfc1982
RobertPitt
uniqid is perfectly predictable. Actually it is only a representation of the microtime it was generatated at. It is in no way random.
nikic
A: 

A little more information is needed. Are you wanting to create a serial key like when you purchase a game or are you wanting a serial for a unique user id.

Are the serial numbers needing to store information such as an expiration time/date?

@nikic - all rand's use time as a base for starting the random generator. That is why the DoD uses lava lamps. They have a whole room dedicated to lava lamps and shine lasers on them to randomly create a unique key.

Edited:

Well what you need to take into effect is what method your C# application will use to communicate with your site.

You will need to create a key with php and store it in the database so that the C# can confirm the serial is a correct one.

You then need to figure out if the PHP will return another value so the C# application is aware the key was authenticated or not.

What I have done in the pasted was create a public key and private key. The public key would be given to the user to validate the product. When they validate the product or login to the system the public key would be checked against the database and the return value would be the private key. During all the interactions with my C# program should the user need to check for updates or pull information from my server the private key would be added to the query to the server to confirm the end user was legit.

Another method I have also used is the above but added additional checking to confirm the user wasn't sharing the key. The C# application would obtain the serial number of the processor in the computer and upon registration of the application it would save it to my database. Then if someone else tried to register the product with the same Public key but different serial number of the processor it would throw an error and they would need to contact support. You can do this to allow 5 different machine ID's or how every many you want.

Creating the registration key is very simple as you really only need to create a random string with an offset (such as the users name).

You could also however create a registration key based on a name or company name that someone provides and add that algorithm to your C# program. The downside to that is C# source code can be decompiled easily the algorithm can be found to create a registration code easily without someone actually paying for the product. By adding in a server that does the authentication it is much more difficult for someone to generate their own serial key.

jostster
lets say i have a product, such as a application, this application requires a serial system, i want to generate a serial in PHP that can be checked and validated within C#, what factors do i have to employ into a script to be able to generate and verify A a key regardless of what interpreter.
RobertPitt
I edited my answer to show some examples of what I have done in the pasted.
jostster
+4  A: 

If your application has a connection back to the server it's trivial, just generate random tokens, store them in a database, and require the application to check back with the server before running. However some customers may find this requirement unacceptable. (I personally will never buy any software with an internet activation requirement. I want to buy software, not rent it.)

For keys with genuineness checkability without having to have a connection back to the server:

  1. On the server, generate a random unique token.

  2. Use a public key cryptography scheme (eg. RSA) to sign the token with a private key that is kept secret to the server.

  3. Encode the unique token and the signature together using some binary-to-text scheme (eg. base64, or just using 2-9A-KMNP-Z symbols for safer typability). The encoded combination is your key or serial.

  4. Embed the public key matching the server's private key in each copy of the application, and have the application prompt for a key at install time. It can split the unique token and the signature, and use the public key to verify that the signature is valid for that token.

This approach requires you bundle some crypto libraries with your software, and most algorithms use quite long signatures, for security, which will make your serial numbers pretty tedious to type in. It's OK if you expect users to copy-and-paste the numbers.

For these reasons many software packages use a less-secure key validation scheme where the checking algorithm is wholly built into the client. This might be a hash, eg. the last four hex digits of the serial must match the lowest two bytes of the SHA1 hash of the rest of the serial combined with a ‘secret’ key. However, since the key has to be bundled in the application, it's possible for a hacker to look at the app code and extract the ‘secret’ key, allowing them to write their own key generators.

That's why for some programs you will see ‘keygens’ available: the app used a less-secure checking algo which left enough information in the application to allow the cracker to reproduce the key-making process. For programs with a more secure setup based on public-key crypto or internet activation, you typically see a ‘cracked’ version of the application instead, where the checking code has been altered/removed.

...which kind of demonstrates that whatever you do, you're still not going to be able to enforce honesty. So don't worry too much about it.

bobince
Good all around information
Fanis
Perfect, Just the type of information i was looking for :), Great read. +1
RobertPitt
:-/ this is exactly what I said.
jostster
A: 

If you want to create random serial numbers centrally, just fetching randomly from an array of numbers and letters should be enough. Use mt_rand(0, count($poolArray)) to get a new index every time and just add that character to your serial until you have say 12 of them.

Generating them in random from such a large pool (26 letters + 10 digits) will almost make sure that you don't have duplicates, but you can always just check for existing ones before you store the new one.

If you have 36 possible characters, and you pick 12 randomly from them to make your serials, that's 36*36*36*...*36 = 36^12 = 4738381338321616896 possible strings.

$pool = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
$countPool = count($pool) ;
$totalChars = 12 ;

$serial = '' ;
for ($i = 0 ; $i < $totalChars ; $i++) {
    $currIndex = mt_rand(0, $countPool) ;
    $currChar = $pool[$currIndex] ;
    $serial .= $currChar ;
}

Distributing them with your code or having your program check for a valid serial is another issue.

Fanis