In my iphone project I always insert UITableView into the view controller as IBOutlet, most times it works well, but random crash will occur when do animation invoked by popToRootViewControllerAnimated. Track it by zombie, find the crash dues to UITableView instance has been deallocated, but there are still system events sent to it, so crash.
I always resolve such issue by either of the following methods in view controller's dealloc method.
tableView.dataSource = nil; (work for most cases)
or
[tableView removeFromSuperview]; (work for some special cases)
Although the crash can be fixed by the above change, but I am still confusing.
Any idea or discussion will be appreciated, thanks in advance.
enter code here
Exception Type: EXC_BAD_ACCESS (SIGSEGV)
Exception Codes: KERN_INVALID_ADDRESS at 0x626f6d37
Crashed Thread: 0
Thread 0 name: Dispatch queue: com.apple.main-thread
Thread 0 Crashed:
0 libobjc.A.dylib 0x33fe0c98 objc_msgSend + 16
1 UIKit 0x364538f6 -[UITableView(UITableViewInternal) _spacingForExtraSeparators] + 58
2 UIKit 0x3645337a -[UITableView(_UITableViewPrivate) _adjustExtraSeparators] + 158
3 UIKit 0x36453218 -[UITableView layoutSubviews] + 40
4 UIKit 0x363ff5f4 -[UIView(CALayerDelegate) layoutSublayersOfLayer:] + 20
5 CoreFoundation 0x30e13efc -[NSObject(NSObject) performSelector:withObject:] + 16
6 QuartzCore 0x33d8dbae -[CALayer layoutSublayers] + 114
7 QuartzCore 0x33d8d966 CALayerLayoutIfNeeded + 178
8 QuartzCore 0x33d931be CA::Context::commit_transaction(CA::Transaction*) + 206
9 QuartzCore 0x33d92fd0 CA::Transaction::commit() + 184
10 QuartzCore 0x33d8c04e CA::Transaction::observer_callback(__CFRunLoopObserver*, unsigned long, void*) + 50
11 CoreFoundation 0x30e7da2e __CFRUNLOOP_IS_CALLING_OUT_TO_AN_OBSERVER_CALLBACK_FUNCTION__ + 10
12 CoreFoundation 0x30e7f45e __CFRunLoopDoObservers + 406
13 CoreFoundation 0x30e80754 __CFRunLoopRun + 848
14 CoreFoundation 0x30e10ebc CFRunLoopRunSpecific + 224
15 CoreFoundation 0x30e10dc4 CFRunLoopRunInMode + 52
16 GraphicsServices 0x34efe418 GSEventRunModal + 108
17 GraphicsServices 0x34efe4c4 GSEventRun + 56
18 UIKit 0x36428d62 -[UIApplication _run] + 398
19 UIKit 0x36426800 UIApplicationMain + 664
20 ScoutFree 0x00099558 0x1000 + 623960
21 ScoutFree 0x00003618 0x1000 + 9752
You forgot to set tableView.delegate to nil, so you can still get crashes, especially when animation is going(as it asks now dead controller for new rows). It's not Apple's defect, it's programmer responsibility to clear out those references. So set dataSource and delegate properties of tableView to nil, then release tableview(by setting corresponding property to nil or releasing iVar like this [_iVar release]; iVar = nil;)
First of all, the ONLY things you should be calling in dealloc are release on your ivars, unregistering for NSNotificationCenter notifications (if registered in init), or setting delegates of UIWebViews and UIScrollView to nil (as suggested by Apple's documentation). If your UIViewController is the delegate/data source of your tableview, there is no need to set those to nil in dealloc (or anywhere else), as when the view controller is destroyed, your guaranteed it won't send any rogue messages, and you're equally guaranteed that the delegate/data source of the table view won't get destroyed before the table view does.
It's highly unlikely that the defect is Apples. What OS are you targeting? If you're using ARC, you really should have few occasions when you need to be mucking around in dealloc. If you symbolicate your crash log, you will get the line numbers and classes from your app that is causing the crash. Symbolicating in Xcode 4 is really simple, you can find info on that here: Symbolicating iPhone App Crash Reports
What do you mean you always insert the tableview as an IBOutlet? If it's an IBOutlet, that implies that you have a table view in a nib file, in which case the table view gets created for you when the nib is unloaded. If you are trying to remove the table view and re-add it to the view for the purpose of updating its information, this is not the correct approach: simply calling reloadData will do this for you, and go through all of the delegate methods again. Are the delegate and data source an object OTHER than the view controller controlling your table?
User contributions licensed under CC BY-SA 3.0