tags:

views:

408

answers:

4

Hi all, I'm getting error as below

Program received signal:

“EXC_BAD_ACCESS”. warning: check_safe_call: could not restore current frame

warning: Unable to restore previously selected frame. warning: Unable to restore previously selected frame.

my app is to get wifi information

libHandle = dlopen("/System/Library/PrivateFrameworks/ MobileWiFi.framework/MobileWiFi",RTLD_LAZY);

open = dlsym(libHandle, "Apple80211Open");
bind = dlsym(libHandle, "Apple80211BindToInterface");
close = dlsym(libHandle, "Apple80211Close");
scan = dlsym(libHandle, "Apple80211Scan");

open(&airportHandle);

bind(airportHandle, @"en0");

when the code reach open(&airportHandle), I received the error but i'm not sure because at this line it stops.

How can I resolve this?

thanks

+2  A: 

This blog post seems to cover the issue.

Suppressingfire
I can vouch for this post. Got me out of a tough spot the other day!
Matt Miller
+1  A: 

EXC_BAD_ACCESS always occurs when accessing memory you already have released. In your sample code, I can't see where airportHandle is initialized, or wheter it is initialized at all for that matter.

If it has been initialized but you just forgot to post that code, you should try checking if you released the handle somewhere.

To debug such an access violation, it is often useful to set the NSZombieEnabled Environment flag to YES. This will cause the Obj-C runtime to log access to released memory to the console. You can find a full tutorial on how to use that information together with Instruments to find your problem.

Johannes Rudolph
+6  A: 

For any EXC_BAD_ACCESS errors, you are usually trying to send a message to a released object. The BEST way to track these down is use NSZombieEnabled.

This works by never actually releasing an object, but by wrapping it up as a "zombie" and setting a flag inside it that says it normally would have been released. This way, if you try to access it again, it still know what it was before you made the error, and with this little bit of information, you can usually backtrack to see what the issue was.

It especially helps in background threads when the Debugger sometimes craps out on any useful information.

VERY IMPORTANT TO NOTE however, is that you need to 100% make sure this is only in your debug code and not your distribution code. Because nothing is ever released, your app will leak and leak and leak. To remind me to do this, I put this log in my appdelegate:

if(getenv("NSZombieEnabled") || getenv("NSAutoreleaseFreedObjectCheckEnabled"))
  NSLog(@"NSZombieEnabled/NSAutoreleaseFreedObjectCheckEnabled enabled!");

If you need help finding the exact line, Do a Build-and-Debug (CMD-Y) instead of a Build-and-Run (CMD-R). When the app crashes, the debugger will show you exactly which line and in combination with NSZombieEnabled, you should be able to find out exactly why.

coneybeare
ObjectAllocator Instrument can be configured with zombie enabled. If it finds it, it throws an alert with zombie address and you can see there in the stack backtrace exactly the call that caused the problem (the call with the latest time stamp)
Nava Carmon
ZombieEnabled is not fullproof though; that only works for NSObjects. If the memory that is triggering that is not an actual object (a struct or something else) then NSZombie will not help you.
Kevlar