views:

364

answers:

4

Hello!

I've a question about a good way to protect a bit my cocoa app from piracy! I know that this is impossible!

So, in my app I've an isRegistered() method that run every time the user launch the app! This is called in the applicationDidFinishLaunching: App delegate ... so if this method return true, the app continue to execute the code ... otherwise an Alert appears saying that the app is not registered and there are xx day to buy a license!

This is a good way? Because, I have no experience in this!

Thank you in advance for your help!


~SOLVED~

First at all thanks to everybody! I think the same thing: any copy protection can stop the piracy! I'm trying only to solve this little bug, even if I know that someone will crack my app again! However, it's true ... the best thing is to improve the app and not waste the time to try make more efficient the piracy protection!

+3  A: 

I am not in shrink-wrapped software business but my friend is. And his observation after 10 years of selling his product was that it makes no sense to create too sophisticated protection because always some one will hack it. You are alone and world is infinite. It is better to invest time/money in improving your software than working on copy protection.

Also keep in mind that around 10% of will never steal and other 10% will always try. Just make sure that those 80% is able to buy your product without any other mayor obstacle. Than you could ignore those nasty 10%. Actually it is a quote from Joel Spolsky IHMO.

So your solution seems to be completely OK from technical point of view and just stay with it.

Michal Sznajder
Your suggestion is Welcome! Thanks!
BitDrink
+6  A: 

The solution you describe requires almost no expertise whatsoever to crack. It is trivial to change your isRegistered() function to always return true. Thus, the effort required to circumvent your protection is a tiny fraction of the effort you would have to spend implementinging all the infrastructure to support users purchasing registration codes.

In other words, you're not getting a good return on investment. There is some debate over whether the return on investment implementing piracy protection (rather than improving your product) is ever good enough (because you pit yourself against people who have nothing better to do than prove they're cleverer than you).

One good way to redress the balance of return on investment is to use pre-existing code such as AquaticPrime. That way, at least you won't have spent so much time chasing rainbows :)

hatfinch
You are right! What you have descried is what is happened with my app! A cracker has replaced the isRegistered() call with a constant TRUE value! AquaticPrime is good but I don't want to use a framework! There is something that I can do to solve this issue? However, thanks!
BitDrink
@BitDrink: You can't do too much about it. No matter how complicated your anti-piracy system is at the end it comes down to a single decision: is it authentic or pirated. The cracker will find that point and replace it with constant true. You can use checksums but the same goes for the checksum checking code.
stribika
And if I don't use the isRegistered() call but I implement the body of that method [isRegistered()] in the applicationDidFinishLaunching delegate, it's a good solution or it's the same thing? (thanks for the reply)
BitDrink
It's the same thing. All a cracker has to do is find the sequence of instructions that checks for registration, and replace the first instruction in that sequence with a jump to the next instruction after the sequence.
hatfinch
And if I execute the isRegistered: method in the init: method of the app delegate?
BitDrink
I would also not call it isRegistered(). In the long run, it won't stop your app from being cracked, but it will at least deter some people if they can't easily locate your registration checking methods.But the other comments certainly hold true: someone *will* [be able to] crack your app.
jbrennan
Thanks for your suggestion!
BitDrink
No, it's not quite the same thing. If `isRegistered` is an Objective-C method, it's *trivial* to replace its implementation. In Leopard, there's a runtime function for that exact purpose. C functions and inline code are much harder to replace (but still not that hard).
Peter Hosey
BitDrink: What's wrong with using a framework? It's an already-written, time-tested solution to a very old problem. Why reinvent the wheel?
Peter Hosey
Thank you for you right! However, I don't want reinvent the wheel ... but I've read that AcquaticPrime has hacked a lot of time by simple replacing it with a fake framework!
BitDrink
Huge, giant companies with more resources than you have had in your entire life are unable to stop piracy. There is no foolproof method. At some point you have to say, "I'm better off using this effort to make my program better so more people will want to buy it."
Chuck
A: 

This is a good question. Having read the answers, I think what BitDrink was really getting at was this: we know that an isRegistered() function is dead simple to hack. With the understanding that any protection system eventually will be hacked, what are some strategies for writing a function that's harder to hack than an isRegistered function that returns a boolean?

Fundamentally, any copy protection system will eventually have something that looks like this:

if (program is registered)
    let the program continue
else
    nagging message
end

Any hacker with a copy of GDB will eventually find that first line and write a tiny little patch to strip it out. Most copy protection systems focus on security through obscurity, i.e. making that line hard to find. You can also make this system more robust by signing the binary and checking the signature, but you'll just add another hoop for the hackers to jump through. They'll eventually find your public key and change it to their own public key so they can replace your signature. However, I believe this will significantly slow them down. Leopard offers a code signing utility, but I don't know if it can be used to prevent incorrectly signed applications from running at all.

There's no perfect solution to this problem, but there are two main things to remember:

  1. your registration system will be broken. There is absolutely no way around this.
  2. your reigstration system is a barrier between the user and your program. You should optimize for the (hopefully majority of) legitimate users and make this as easy to do as possible.
Alex
+2  A: 

Hi,

it's almost never worth implementing your own anti-piracy system, because you'll almost always spend a lot of effort on something which can then be broken very easily. Rely on a shared implementation - in this case a framework like AquaticPrime (lots of people on the macsb mailing list recommend that one) - and you're effectively relying on the framework being good enough to protect your own app as well as all the others.

The code signing framework on Leopard and later allows you to sign your code such that if it's ever tampered with, it will refuse to run - see the documentation of the kill option in the manpage.

Graham Lee