My thanks to OP and other contributors! Great info on this and prev. thread.
I'm getting ready to release my first iPhone app and have a friend with 4:1 piracy ratio on his app (4 pirates for 1 paid)...so I find myself here, starting to work on (c) code.
I wanted to contribute some general (non-iPhone) specific advice that makes it harder to crack at the assembly level. This is my first project using Xcode and IPhone, and most of it we did in C instead of Obj-C, so some of these may not be applicable to the Obj-C pre-processor.:
BTW - If you've never loaded a stripped app you've written into a RE app like IDA. download the free demo and give it a try. You'll be surprised how easy it is to see lots symbols and function names, especially if you're using ObjC or C++.
So, some basic stuff:
Never do this:
Code:
if( isPirated() ) {
exit_routine()
}
All a cracker has to do is nop your call to exit_routine() or make isPirated() always return 0x00. Both are incredibly easy.
Obfuscate your copy protection routine names using the preprocessor. For example:
Code:
#define isPriated isAudioEnabled
The preprocessor basically performs a search and replace when you use a #define like this. If the symbol for the isPirated() routine ends up making it through to the executable, it will be called "isAudioEnabled", but in your source you use isPirated() so it's easy to remember what you're doing.
Crackers usually ONLY check some basic functionality for a short time before assuming their crack succeeded. Delay your reaction somehow, and try not to make the reaction exit the app. For example, if you detect a pirated copy, wait until half-way through the second level and display something like a "missing sound asset" error message and hang the app. (Make sure the error message you show is not easy to find - put code in lots of places to show that message, even if they're inside if-blocks that never get executed.). First, the cracker will suspect there's some other problem. You'll get users asking for support and/or complaining on forums about the issue. Normally legit users will reply back that it works for them, and you can put a note in your FAQ something to the effect of "we have seen this issue with some illegal copies of the game. If you experience this on a legitimate copy, please re-download from iTunes." You could also just do something annoying like XOR all the PCM audio at some point, or change some of the sprites into solid colored rectangles.
Call your copy protection check routines through multiple references, and store references in an unrelated structs. This makes the calls much harder to find. The reference is also handy for checksumming your protection routine.
Pass a variable to your copy protection routine that has subtle influence over its success or failure. In your code, sometimes call checks you know will fail. If they don't fail, the copy is pirated (probably routine is modded to always return 0 or 1).
Use multiple setjmp() and longjmp()s to react to piracy triggers. They're hard to trace in assembly and most programmers have no idea what they do.
Obfuscate important strings with ^0xFF on each chars. It makes text look like binary data and is easy to forward/backward encrypt. It's not hard to decrypt but makes it harder to find strings than just looking with a hex editor or software like IDA. If you want to get facny, you can do something simple like char[1-n] = char[1-n] ^ char [0-(n-1)] to make it a little harder.
Release your own "0-day" cracked version of your own software the day before it hits the iPhone store. Grab some other cracked app and copy the cracker's template. Doesn't also hurt to insult other cracking teams in the release. Put it up everywhere you can. Make this version of the app just a little more than any free demo version, but not the full app, and have it stop with errors or some sort. Think of this as your "second" free demo for the piracy crowd. It's a great marketing tool. If you don't want to use this as a marketing tool and are feeling malicious, have it email soft-core gay **** to everyone in the user's contact list.