C# Application License Components and Controls [closed] - c#

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 7 years ago.
Improve this question
If I have 5 target computers and I am going to install my application to one of those target computers. How I prevent users from copying my application to other target computers?
To make it clear, I don't want them to copy my application after installation (They should not copy my application from the installed application folder). The problem is now I setup and deploy my application using Visual Studio 2010 Setup and Deployment, but anyone can copy my application folder after the installation for example, my application folder (exe, DLLs, and resources) locates at "Program Files/MyApplication". They actually can copy my application from that folder and paste it to other computers then use it. Of course, they can copy it but I think they should not be able to use my copied application right? Is there a way to protect them copying my application? I have to write an additional code?
I am really new for software distribution. Please guide me what I have to do.
Thanks

You can use Rhino Licensing framework for license file generation. It has LicenseGenerator class which has a Generate method. Here is what it looks like:
public string Generate(string name, Guid id, DateTime expirationDate, IDictionary<string, string> attributes, LicenseType licenseType);
Generate method takes the name of the licensee. Unique id for the license which can be generate as Guid.NewGuid(), the expiration date and the attributes dictionary is a place where you can store a custom key value pair in the license file.
The way it can works is that, you can embed the information of the machine in the license and in the verification phase you can check whether the license belongs to the same machine. This means that you can not copy license file of one machine and put it on another machine because it won't work.
In the license file you can store the following information:
The expiry date of the license
Name of the person for whom the license is generated
Hash calculated based on the system information

The industry-standard way of preventing users from running an application on more than one machine is indeed to lock your product to some parameters of that system. However, you need to think about the following issues to avoid future work or upset customers down the road. Crude systems that don't deal with these issues have given node-locking a bad name, but when done properly node-locking is unobtrusive, flexible and secure:
How will you accurately obtain the system parameters you will lock to? Asking users to read/type them is a common source of error, for example by mis-reading an 'l' for a '1' or a '0' for an 'O'.
The MAC address is commonly used for node-locking, but this is a poor choice as the MAC address can be set by an admin under many operating systems.
Say you lock a license to several parameters of the system. What will happen if the user does a minor system upgrade, so causing one of them to change? They won't be happy if your app suddenly refuses to run.
Users will want to move their license to a different machine at some point. You'll need to think about how you support this without making it a security hole.
Users machines will crash - it happens. How can they get their license running again on their new/rebuilt system?
Just some issues we've encountered and dealt with in our solutions. Hope this helps.

I use Infralution License Tracker. It is payware but allows for licensing of some part or all of an application. It also allows for key verification on on-line verification. It is possible to use customer information to generate the key so it should be feasible to register using information from the target computer.
http://www.infralution.com/licensing.html

When you want it really easy you can use LimeLM.
Simple online-verification with a trial option.

You need to use machine-locked / activated licenses to prevent this. This ensures that the license can only be validated from a single machine - if license validation fails, you can decide what steps to take - whether to exit the app, show a message to the user, allow a grace period, etc.
Try CryptoLicensing which supports activated / machine-locked licenses.
DISCLAIMER: I work for LogicNP Software, the developer of CryptoLicensing.

Related

Secure network traffic c#

I'm developing a program in C#.
It connects to the internet to see if this copy is valid.
Currently I'm just sending the licence key and getting a response (0 or 1) if the key is valid.
The problem is that some users just fake the data with some packet capturing tool and replay it.
So the application is very easy to crack. How can I prevent this?
Here is what I essentially want to prevent:
Network replay attacks
Authentication "emulators"
It should be impossible to find out what data is sent.
Maybe I should add the current time and then encrypt the packet ?
So it's always different ?
Attention: Please don't warn me that it's easy to crack the application itself by modifying it. I know that. This question is only about the network part.
If you use SSL or HTTPS then you don't have to worry about users cracking the data packets. This is easy because the libraries already exist and are easy to implement. With C# and IIs for example it is just a matter of installing the certs and changing a few configuration items. (Maybe a recompile with some slight code changes).
Assuming you actually want to prevent license abuse there are far better ways to do this. The "phone home" approach is easy to roll yourself, but as you've noticed it's full of holes.
Disclaimer: I work for a company that makes commercial tools to solve these license management and copy-protection issues. There are other similar products available from a variety of vendors.
This isn't that different from thinking about how to do setup for your application. Choices are roll your own or buy an existing 3rd party toolset. Rolling your own at first blush make seem cheaper, but that's perhaps only because you haven't really discovered all the true requirements to create something robust and reliable. The 3rd party tool vendor needs to charge for their products, but they've spent years discovering all the issues with particular problem set and have solved the problems. So that eliminates work for you and leaves you free to focus on where your application can add value.
The difference is if you get setup wrong your users will be irritated; if you get copy protection wrong your product will be pirated.
In any event, reducing license validation checking to a binary "either/or" condition is extremely easy to crack--doing that check over the net makes it 10 times easier (record playback attack). Modern approaches encrypt the executable and the license is contained in the key to decrypt it (this is an oversimplification since the actual methodology includes a lot more complexity to make it virtually impossible to get around). Only by having a valid license can the executable be decrypted on program load and run.
If you want to do it the way you've described, consider this:
Have the app use a predictable, changing value (such as a lookup from a table of random numbers coupled with some external value like time) to create some kind of hash. Have the server implement the same code. The server sends the hash to the app, which compares it to its own hash. If they match, the app is allowed to run. If they don't, it errors out. Since the hash is different on ever startup attempt, recording it over the network won't allow the user to get it to run the next time it tries to start.

Implementing node-locked license: public fields with signature versus complete encryption

Background
I need to implement a simple node-locked licensing mechanism (i.e. the license needs to be valid only for a specific physical computer).
I intend to use an asymmetric cryptographic algorithm such as RSA.
Here is how I intend to organize the basic licensing "workflow":
The application that needs to be licensed reads a piece of data that uniquely identifies the computer (it is currently running on). Let's call this data "computed ID".
User requests the license by sending the computer ID.
Based on the computer ID, the license is generated and protected (either by full encryption or by signing) and sent back to the user.
The application can then compare the license with the actual computer ID and refuse to run if they do not match.
Note that computer ID will not be particularly sensitive (probably just a MAC address and possibly HD serial) and does not represent a secret on its own.
Question
The dilemma I have is whether to:
encrypt the computer ID (both in the license request and in the license itself),
or to include it as a plain text (in both request and license) and just add a signature (in license).
(1) If I choose full encryption, then I'll need two pairs of public/private keys - one for each direction (one for encrypting the request and decrypting it before generating license; and one for encrypting the license and decrypting it by the application).
(2) If I choose to use signature, I just need one key par - private key for signing the license and public key for verifying the signature when application runs (so it knows the plain text computer ID in license did not change).
The approach (2) looks simpler to me, but is it as "strong" as (1)?
I'm implementing this in C#, but I'd like a general "high level" advice on pros and cons of each approach, regardless of the implementation details.
Since this is my area of expertise, let me jump in... It seems you are trying to create your own activation system starting from scratch. May I ask why you are doing so, rather than just using a commercial system?
In the early days of using activation to protect software licenses a number of companies took the approach of developing their own systems without having deep expertise, and their ignorance of what it took to make a secure, user-friendly activation system gave activation a bad name. So, in the interests of helping you not have to painfully re-learn these lessons and irritate your customers, here are some of the things you need to think about:
How will users activate their license if they don't have a network connection to the server, or their connection is blocked by a firewall?
You said you are node-locking your application to some parameters of the user's system. How will you deal with someone who makes a minor upgrade to their system, causing a node-locking parameter to change? Note the MAC address is not a good choice for this, even though it is commonly used, as the ease with which the MAC address can be configured on some systems means MAC-address node-locking is insecure.
A user's system crashes - how can they get their license running on another system? (and how can you know they are telling the truth about their system crash?)
What if a user wants to move their license to another machine after a while, say from their desktop to their laptop. Can your system allow them to do this without it being a security hole or an annoying manual process requiring your support?
How will you secure your licenses against key tampering, spoofing or tampering with the licensing code etc?
From your post it seems you just want to enable the whole application for now. What if in future you want to activate time-limited trial or subscription licenses, configure product features or enable certain modules etc. Will your activation system support this or will you have to re-build it?
Some companies don't want any clear-text information about their systems going over the Internet, so you may want to encrypt the uploaded system details from the get-go.
Just some things to think about.
As your computed id works only on the machine where the computed id can be reproduced it is actually not really a problem if you transport the computed id as plaintext. even if somebody steals it, he wont be able to use it.
If somebody manipulates it through the transport you will recognize it too (as it is signed)
But: it depends what kind of computed id you generate. If you dont use a appropriate algorithm someone could get some information about the system on where the computed id got generated (which wouldnt be appreciated by your licencees)
For that you should use a "save" hash function with no (or non predictable) collisions.

Decrypting EFS encrypted files

I have a number of files that were encrypted using EFS on my old Windows XP installation. I installed Windows 7 and now I can't access these files. You can read about the whole embarrassing situation here.
The good news is that I have keys that will allow the files to be decrypted. I know this because I used EFS data recovery and it was able to decrypt a file. It also identified that I had some usable key files of some sort (master key and private key).
The problem here is that Elcom want's $150 for their tool and what I have encrypted is not worth $150. Is there a way that I can do this myself, programmatically?
EDIT: This link is awesome...EFS recovery
I found the following resource:
http://www.beginningtoseethelight.org/efsrecovery/
It outlined how I could recover my files. I did have all the keys so I can decrypt the files if necessary. However, I gave up on this because I didn't want to trash my existing system in order to recover the old one. There's still a chance you can torch the new Windows installation and I didn't want to deal with all the backup stuff.
The only other answer I know of is to use a tool called RECCERTS.EXE that Microsoft Product Support has available to those who call. I can't even begin to imagine why after years of these kinds of problems people have had with EFS over and over, Microsoft still hasn't released this tool as a free download. It searches any available files it's pointed at to look for all the remnants of the keys and metadata necessary to decrypt and use the RSA private key that your previous OS install used to decrypt the EFS-encrypted files on your system. It works awfully well, but from what little documentation there is on the web (i.e. MSDN Social forum postings - latest in 2009), it appears this tool is still only available if you can find a way to convince MS Product Support to send you a copy. It appears that the cheapest official doorway here is the $99 email incident, but I wonder if they'd refund your money if you demonstrated that this fixed your problem (cf. how they used to refund - and may still do so - PSS incidents if you were able to demonstrate that there was a bug in their software for which you're calling). Not saying this is a bug, just the painful byproduct of a dubious design that doesn't warn users to take appropriate and explicit steps to avoid these recovery nightmares.
The only other possible solution is to search the web for RECCERTS.EXE and see if there are any locations where it's been made available for download. Many of such sites use legit filenames as "lures" to get you to download something that turns out to be malware, so be very careful if you take this approach. However, if your time is worth less than $99, then you just risk hosing a Windows install with nasty malware - and having to wipe & recover the system. [Just make sure there's an offline copy of the files you're trying to recover, in case the malware infects or corrupts an online, mounted copy of those files.]

How to make my program not run on other computers?

I have an assignment, and it has (amongst others) two demands:
make an installer
make it so that if it is installed on one computer, anyone trying to run the same files on another computer will fail.
I'm using VS9 (2008) express, I think I can do the installer part, but I'm not sure how to do the "security" part. I don't need any hard to crack safety, just a dumb condition that will stop most users from copying the files to another computer. (Like checking the MAC address).
Any ideas?
EDIT:
I would like to check the MAC address but I want the program finalized during installation. Meaning that after I install I can't move the program to another machine. It also does not have to be a very smart or difficult condition, just bare minimum. I just don't know how to do it in the installation.
EDIT:
It's sad I don't have the complete VS then I would be able to do it easily.
If you're looking for some way to mark the first computer as the "authorized" computer, then you need some external service you can ask for permission to launch.
The first person to ask permission would be allowed, the rest would be prevented.
You'll also need to come up with some way of identifying a particular instance of your application that's different for every install.
If your app needs to be authorized for the machine, then you will need to calculate some fingerprint for the machine it can use each time (eg across installs).
[Edit]
This approach is useful when you're worried about copies of the installer being distributed as well. You did specify that its ok to install on multiple machines, so in that case MasterMind's approach is superior. It will work, and does not requires a 3rd party server
[Edit 2]
If you're looking for info on how to build a custom installer, try here
First of all, come up with some function to generate a unique PC signature, like Windows does for activation.
Your installer will be creating this signature and writing it to a local file (better encrypted). You can create a simple console executable to generate this file and include that executable into your installer package, setting it up to run silently after the successful installation.
Your program when starting will be creating the signature again using the same algorithm and comparing it to the one created during installation. If the new signature is different from the original one or the signature file is missing, then exit without loading the UI.
ADDED: If you don't need it very complex, you can just choose a few unique values like the MAC address you suggested, maybe the hard drive serial number, mainboard serial number, concatenate them into a single string and generate the hash out of it.
This approach will allow for an unlimited number of copies to run (but each installation will only be workable on one single machine where it was installed). If you stick to the identification by hardware (or OS product key as well), then the application can run on various OS installations on the same machine.
This strategy, however, implies that you control all installations (or perform them yourself) or absolutely trust your client not to install additional copies elsewhere or distribute your installer. If you need that kind of protection as well, then you should consider product activation. It can be quite complicated if you do it yourself. There are however third party products to help you. Some offer product activation services: Google: activation service
Once you have a decent fingerprint, the rest is easy. Personally I'd take something like the MAC address and the windows product ID (at HKLM\Software\Microsoft\Windows\CurrentVersion\ProductId) and use a hashing algorithm to get something reasonably obscure.
edit:
Here's a question that shows you how to get your MAC address as a string:
Read MAC Address from network adapter in .NET
Then grab your windows product ID (in case they don't have a network adapter) from the above registry key. Concatenate both strings and do a GetHashCode() (or use your favorite hashing algorithm) on the result. This is a simple way to get a UID for a computer.
Write the hash to a file or to a registry entry when your installer is executing and check it when your program starts up.
Consider using two or more values that potentially identify the machine, e.g.
Windows product code
Volume serial number of the C: drive
MAC address of an ethernet interface
And if just one of these changes but the others match, update that one value in the registry and continue running normally. Hard drives get replaced (regularly), Windows gets upgraded (occasionally), Ethernet adapters get replaced (rarely but it does happen.) It can be very frustrating when old software stops working because of this.
Bare minimum answer, assuming the only requirement here is that the software should run if installed through the installer, and won't run if copied to another computer:
Write a simple key to the registry. Most likely your product's version number, incase they copy a newer version to the computer, it has a different number to check for.
In your software, just make sure this registry value exists.
For packaging installations, I enjoy using NSIS which has simple methods for writing to the registry.
I like the idea of checking the MAC address.
I have also seen product key/online activation combinations where you enter the product key and the software contacts a web service that logs the product key and # of installs.
This isn't the most secure option or anything but you did say it didn't have to be smart...
On install, you could set a program variable to be the machine name (or a hash of it if you like).
Like:
myProgram.Properties.Settings.Default.Machine = System.Environment.MachineName;
myProgram.Properties.Settings.Default.Save();
then check that on startup:
if (System.Environment.MachineName != myProgram.Properties.Settings.Default.Machine)
{
MessageBox.Show("Can't run on this computer");
this.Close();
}
To get the installer to only work for one machine, you'd pretty much have to build it for the target machine. I dont think it would be possible to make an installer that assumes the first machine it sees is it's mommy and is attached for life.
-1 for clinging to an antiquated license-restriction policy that is a poor practice in general. Hardware dongles and "device detection" are SO 1990.
People own more than one computer. They buy new computers. They upgrade their computers. Computers break, resulting in replacement of motherboards or network cards.
All of these, given your design, will result in honest, paying customers being locked out of what they've paid for and will have to call you for support to "reset" their activation.
And each time you do so, your overhead will increase by, very likely, more than the actual cost of a license.
I'm not suggesting you give up and just send your app off to the torrentverse, but you should think more creatively about how to allow customers the freedom to use what they paid for, keep your support costs low, and discourage pirates.
One creative solution would be to cache the user's settings on your server, keyed by their serial number, and synchronize them every time the application starts and is connected to the Net.
This will allow a user to install the app on, say, both a laptop and desktop, and will actually be a value-add for customers because their settings are synchronized between devices.
But it actively discourages users from sharing their license key, since doing so would mean they would be sharing their settings with every pirate user, or that they would have to remember to stay disconnected from the Interwebs when they open or close the app.

A different Approach for anti-virus . Am I going in the right direction?

I'm currently conceiving a system that works like an anti-virus, but also uses the White Listing i.e
Preventing Viruses from Running by having a database of Known legitimate Programs
Yes , there is the Windows UAC, but still many viruses "work around" it. I'm planning on a more reliable system.
My system has also a database of known threats (cryptographic hash).
Is this approach viable,
What are the possible loop holes in this approach
I understand that there has been a lot of attempts at this. But still I want to try it out.
I'm planning to use C# and .Net for a prototype may be i'll move on to C++ for performance later
Update:
Thank you all for your time and thoughts.
I decided to do some more research in this area before actually designing something
Espcially as pointd out below the Zeroday threat problem
What about DLLs used by executables? Do you hash them too? A virus can replace a DLL.
This has been brought up before, and there are products out there which do that. (Faronics Anti-Executable works like this)
There are two main problems with this approach:
A virus can embed itself into any file; not just EXEs. Programs can load DLLs and other bits of code(macros, scripts, etc), and programs can contain bugs(such as buffer overflows) which can be exploited by malicious documents and other files.
Every time you patch a system or otherwise legitimately modify the software, you also need to update the white list.
There is products like Appsense Application Manager that do this already. It was temporarily pitched as a security product but they changed tact and focused it on licensing. I think it's because it didn't work too well as a security product.
If you are planning to work with a limited set of applications and you can work with application developers you can use a code signing model. You can find a similar approach in most mobile operating systems. You have to sign all the executable modules including libraries and need to verify they have a valid signature and not modified using a root certificate.
If you are only planning to white list applications based on their hash value you need to make sure your white listed applications verify any modules they use before they load. Even if the applications/installation files are digitally signed it does not guarantee that a library will be modified later in a malicious way.
In reality, it is not even enough to only verify executables and libraries. For example, Xbox Linux hack utilizes a malicious save file. It is a specially prepared save file that causes a legitimate and signed application behave in unexpected ways. And, of course it is not possible to white list a save file based on its hash value.
Another problem with keeping a database is zero day attacks. You need to be ahead of the curve for creating hash values for new attacks and propagating these updates to your users otherwise they will be vulnerable all new attacks. Unless you only allow only white listed applications to be executed and that would be really restrictive.
IMHO, it is really difficult build such a system on open platfom. Good luck with it.

Categories