(Friday morning, fresh with coffee and a need to exercise my fingers...)
My process is similar to what Simon describes but goes further.
- I get a unique ID from the OS. Since the method for this varies the code looks for key markers in the OS.
- Then I get the DBMS unique ID, the method for this is of course unique to each platform.
The result of the two above guarantees me that I can identify a unique system.
- From there I encode that data along with the ID for the software and version ID into a long string.
- The user is asked to email the string.
- My parser logs the OS, DBMS, product, and version, along with a manually entered company name. This allows for tracking upgrades, reinstalls, and license movement.
- A key is generated with the exact same details plus a termination date. I use a far-future termination for permanent keys.
- The key is emailed back and saved by the user in a data file. The product can be reinstalled and will run with that key.
- In addition to activating a specific product and version, it also passes in a set of features, identified by a couple binary-encoded bytes.
Since my products run on most DBMS/OS platforms I need to send a different install package for each permutation (usually just an account to be restored). I use a single code base and the code includes platform-specific hooks which are activated during a build process on each platform. So if I'm building for D3 all of the other code is commented out during the build. If you've ever looked at the AccuTerm BASIC source, the approach is the same. I use a version of Kevin King's XBASIC to toggle the platform. (See FOSS4MV)
My source code (for the most part) does not include readable strings for the activation - messages from the activation are decrypted at runtime. This is to avoid the possibility of simple binary/debugger changes on the object modules. Depending on the platform, the build process strips the object code of strings and recognizable variable names. Yeah, I took it that far, primarily because this was going to be marketed as a NebulaSecure package of its own and I wanted to make sure it was bulletproof.
I separate the custom encryption algorithms from the functional code so that I can replace it if necessary. The string from the end-user includes an encryption version, so the decryption code will use the right algorithm based on the specific string. The algorithms include character movement, byte counting, bit shifting, and checksums. That was a fun system to design and code but looking back it was serious over-kill.
I did not implement a cURL interface for automated activation, though I wish I had and will probably do so in a new version. The issue here is that many sites are very locked-down for security and people get very uptight with "phone home" technology, though that's changed significantly over the last decade. So this needs to be implemented as an option, not the only mechanism. When you don't have personal contact in the key exchange, the automated function needs to be able to distinguish between a reactivation in the same environment versus a re-hosting by a given end-user. Another issue is that when it doesn't work people get frustrated and then more time is spent down the rabbit hole of network diagnostics for an activation process - and even if your software works flawlessly that's what people will remember. So again, I opted to avoid that but should have added it later to simplify the activation for other sites when it was possible.
The only known flaw with this security mechanism involved the OS-level integration. Windows Update modifies the OS-level markers that I was using, and for some reason a Daylight Saving Time change did the same. We lost a few clients because their software kept deactivating and I couldn't fix it fast enough. For Unix platforms I needed to occasionally change the mechanism to get the unique system ID because the OS providers sometimes change it (didn't see that one coming). And there's a RedBack bug over AIX which affects how my software interacts with the OS. A new version of my code uses OS-level code (rather than BASIC) to get a disk signature, avoiding OS issues. But again, I feel this process has gone down the path of over-development and I haven't yet put this into full production. It also adds another component to the package, which some people find objectionable.
The good thing about the system is that we have been able to track the movement of licenses across systems. When someone says they're just reinstalling their DBMS, it's confirmed with the same OS/hardware ID. When they say they're migrating their system from a dead hard drive, we just issue a new key, no questions asked. But I can see when another request comes in for another key on the old "dead" hard drive with the same OS/DBMS markers.
While it has worked for many years, without incident except for the above situations, I think my system was a fine example of over-development. While every
part of the process seems necessary, at the same time, MV sites simply
don't share code. (Heck, as discussed in this group we can't even get people to share FREE code.) A complex activation mechanism (even as simple as "run this command and email the results) only interferes with
the user installation experience. I'd prefer a simpler, more interactive, and
personal activation process, as long as it's non-intrusive and not time
consuming. The detail in a system like this depends on the Value of what you're trying to protect. For my software that only costs $200, the activation is severe over-kill, but it was designed for much more expensive packages, and for that reason alone I've held onto it.
The take-aways:
- Decide what your supported DBMS and OS platforms are. Don't get blind-sided by people installing on unsupported platforms.
- Consider end-user security concerns and offer options (even for-fee if you need to accommodate unique environments)
- Don't over- or under-engineer for your purposes.
- Related, decide the trade-offs of end-user convenience (and UEX) with your need to protect your assets.
- Trust, but verify. Most MV people aren't inclined to run away with software. Don't hassle your good clients in an attempt to protect against the bad. Is it really a financial loss if some sites bypass your system and get your software illegally? Or does that just serve to increase your user base? Weird, yes, but worth consideration as for some companies this has become an unexpected part of their business model.
[AD] Rather than writing your own system, if you'd like to use mine and are willing to pay something for it, I'll be happy to address those issues and provide it as a package. Really, you could spend months developing your own package (or years and still not get it the way you want it). Are you selling an application or security tools? This kind of development is 100% expense with no ROI, and should be minimized.
As another option, Brian Leach has mvInstaller (
http://brianleach.co.uk/pages/deploy.htm) I don't know if that includes a licensing mechanism.
HTH
T