|
One of the biggest problems developers have when building apps for the iPhone is memory violations. A lot of developers, especially those who come from a Java or .NET background, have trouble adjusting to an environment where they need to manually keep track of reference counts and they need to be explicitly aware of their own memory management.
I've known quite a few developers who tried their hand at programming for the iPhone and they threw up their hands and quit when they started trying to track down memory problems. I'm certainly not condoning that kind of behavior, I'm just recognizing that the lack of built-in garbage collection represents both a learning curve and a frustration obstacle for new iPhone developers, whether they've been doing other programming for 2 or 20 years.
Thankfully, there's something you can do about it. One of the biggest problems people get is an EXC_BAD_ACCESS error that terminates their debug session, but the callstack is empty and it's nearly impossible to figure out which method call caused the problem. There are several causes for EXC_BAD_ACCESS but the #1 most common cause for this is the attempt to send a message to a released object. The problem arises from the fact that since the released object isn't there, the bad access occurs and the call stack goes away before the debugger stops.
This is where NSZombie comes in. NSZombie is quite possibly one of the coolest, most clever tricks I've ever seen in a programming environment. The way it works is, when you have zombies enabled (will show you how to do this in a second), a released object becomes a zombie when released. What this really means is that instead of deallocating and moving on, the original object is deallocated and an instance of NSZombie is left in its place. The sole purpose of NSZombie is to yell at you whenever someone tries to send it a message. Any message sent to a zombie will halt the debugger and put an entry in your console log telling you that you just tried to send a message to a released object.
I cannot even begin to describe how useful this is. This preserves the call stack so that you can see the exact line of code that sent a message to the released object. While this won't necessarily tell you what you did to prematurely release the object (premature release... too funny), it will tell you which object was released and what message you were trying to send and it'll preserve the call stack to give you other valuable debugging information.
To enable NSZombies all you need to do is double-click the application file in your "Executables" group and go to the parameters tab. At the bottom you'll see an area to configure environment variables. Add an environment variable called NSZombieEnabled and set its value to YES. Your screen should look like the screenshot below:

Now that zombies are enabled, you will be able to run your application and know that when you send a message to a released object, you're going to get a nice friendly execution termination, complete with call stack. You'll know which message was sent and you'll know which objects have been released because when you hover over them after the break, you'll see which ones are concrete instances (still alive) and which ones have been released (they'll be an instance of NSZombie).
Moral of the story: Not only are the undead good for entertainment value and destroying the earth in an unforgiving plague of destruction, but they're handy debugging tools as well.
Thanks for the great tip. There's a lot of good stuff you can do with
environment variables - for example, setting OBJC_HELP=1 prior to running
dumps out a bunch of messages that you can debug.
This and many other great tips are documented in the technote "Mac OS X
Debugging Magic":