我正在通过一个有点棘手的iPhone崩溃,看起来罪魁祸首是NSString过早发布.我已经打开了NSZombiesEnabled并且可以看到NSString在崩溃时是一个僵尸.但是,我无法确定对象何时被释放/解除分配 - 我已经通过我的代码查找发送到此对象的释放消息,并在这些位置设置了断点,但它们没有被击中.
我认为这可能是一个线程或自动释放问题,因为它是间歇性的,但有没有办法通过Xcode调试器挂钩到objective-c运行时来告诉对象被释放的确切位置?或者有更好的方法来诊断这个问题吗?
如果您可以在模拟器中重现崩溃,您可能希望研究使用该malloc_history
工具.(它有一个手册页.)你需要设置一些环境变量:我通常通过Arguments窗格中的"Edit Active Executable"屏幕设置它们,然后使用那里的复选框启用/禁用它们.确保在设备上进行调试之前禁用它们; 如果启用,程序将尝试写入/tmp
沙箱不允许的内容.
我发现这个工具结合NSZombie
使我可以跟踪alloc/premature-release/access-after-dealloc错误.一旦NSZombie
报告获得解除分配的对象,你可以使用malloc_history
摸出对象被分配时.这通常会让我走上解决问题所在的道路.
我发现宝贵的另一个工具是铿锵从LLVM项目.它仍处于开发阶段,但它们经常为MacOS-X生成对我来说非常稳定的二进制文件.特别是,它了解Cocoa内存管理策略.使用它很简单:
% cd ${DIRECTORY_CONTAINING_XCODE_PROJECT} % xcodebuild clean % scan-build -V xcodebuild
这将完整构建您的项目并生成一份报告,列出该工具找到的任何明显错误(包括引用计数搞砸).