protect Java Application by licence or key [closed

2019-01-30 05:11发布

问题:

I want to make an desktop application that only runs on machines that have key or licence. How this can be achieved?

回答1:

This depends entirely on how secure you want to make it...

The problem with Java is that you can reverse compile it. So if someone wanted to, they could download your software, reverse compile it, and then remove whatever security you have put in place (and then redistribute it if they wanted).

This is only a problem if you plan on going mass market and selling it and piracy would actually be a problem though.

If you're not concerned about this, then you can either go for online, or offline checking.

The company I work with uses the online method; there are a few steps:

EDIT: I've since changed how this works, as the old way was a maintenance nightmare.

  1. A license file
    • (this can contain whatever you want in reality, it just has to be unique per user. Most people normally go with general garb;
    • name
    • company
    • email
    • and then a key. i.e. the JDU8-AJS9-88DF-SASF-ASF9 kind of thing you often see.
  2. The program generates a hash from the license file.
    1. put all the data from the license file into a string
    2. pass the string to a hashing function this page can show you how.
  3. have the program check online (on your server). The data gets encoded in an HTML request (post/get/json/whatever you want) and submitted to your license verification page, which then verifies the data. Included in the data is a randomly generated string, which is used by the verification page to generate another password. This is then returned to the program, which has also used the random string to generate its own password. If the two match, the program starts up.

To generate the keys, just use the same hashing function, and then upload the hash to your server.

If you want it to be offline, you could include the hashes in the code I guess and check against them there.

I should point out, however, that I'm not a security expert by any means, I just develop for a company as a portion of a Ph.D. and this is just how I did it.

Edit: this image might be helpful:

Second Edit:

I have now included "offline verification" in the process. It's not really offline verification, it just uses the user as a proxy - they need to access the internet another way.

it works like this:

  1. no internet connection found: supply the user with a 4 digit code
  2. user goes to offline verification page (optimized for mobile use too)
  3. user selects which software they use from the dropdown list
  4. user enters their username (this field remembers entries)
  5. user enters the code the program gave them and submits
  6. webpage provides a 4 digit code, which they then enter into the program, and it starts.
  7. program adds some special data to the license file meaning that this process won't need to be repeated for the next week/month/however long.

every time the program successfully verifies online, it also adds an offline access password to the license file, which means it's robust against temporary internet downtime, and will only stop working if the internet is down for more than a week/month/however long it's set up to work for.



回答2:

You can track licencing of a machine with macIP on online . Even in windows you can write in registry there is no api but still you can do it. Find snippet bellow to read registry -

public static final String readRegistry(String location, String key){
        try {
            // Run reg query, then read output with StreamReader (internal class)
            Process process = Runtime.getRuntime().exec("reg query " + 
                    '"'+ location + "\" /v " + key);

            StreamReader reader = new StreamReader(process.getInputStream());
            reader.start();
            process.waitFor();
            reader.join();
            String output = reader.getResult();

            // Output has the following format:
            // \n<Version information>\n\n<key>\t<registry type>\t<value>
            if( ! output.contains("\t")){
                    return null;
            }

            // Parse out the value
            String[] parsed = output.split("\t");
            return parsed[parsed.length-1];
        }
        catch (Exception e) {
            return null;
        }

    }

And in class level if you want to obfuscate use proGuard .



回答3:

it depends how many customer you plan to have and the distribution mode also. You may use a licence server but this require an internet connection for the customer. You can also use USB dongles to manage licencing.

There are no perfect system you need to make a comproise between simplicity, effort and price.