2013-04-01 44 views
2

因此,我正在對我從測試儀獲得的崩潰日誌進行故障排除時遇到了一些困難。該應用程序與EXC_CRASH (SIGSEGV)崩潰,並且在任何線程的唯一識別碼是在線程6.堆棧跟蹤看起來是這樣的:NSAutoReleasePool發佈視圖控制器?

... 
15 MyApplication     0x002cfcf2 0xfb000 + 1920242 
16 MyApplication     0x00107f26 -[CCViewController dealloc] (CCViewController.m:73) 
17 MyApplication     0x001cc27c -[CCSubmitReportController dealloc] (CCSubmitReportController.m:646) 
18 CoreFoundation     0x36f41c3c 0x36f3f000 + 11324 
... 
26 Foundation      0x35396bd4 0x35387000 + 64468 
27 MyApplication     0x001c794e -[CCGetFeedOperation main] (CCGetFeedOperation.m:102) 
... 

如果您在CCGetFeedOperation看線102,它只是排出操作的自動釋放池在其工作結束時。

所以我想弄清楚爲什麼autorelease池會試圖釋放委託。給委託的引用傳遞給操作類這樣:

@property (assign) id <CCGetFeedOperationDelegate> feedDelegate; 

我能想到的唯一的事情就是我調用主線程的方法,並等待它調用池前完成排水。

invocation = [NSInvocation invocationWithTarget:feedDelegate 
                 selector:@selector(operation:didGetFeed:) 
              retainArguments:YES, self, feedDetailsModel]; 

但是,這仍然不能解釋爲什麼操作的池會導致視圖控制器被釋放。思考?

編輯:順便說一句,我還沒有能夠重現這一點。我只在我們的測試人員和野外人員的崩潰報告中看到它。

編輯2:自動釋放池非常簡單,它在操作的main方法開始處分配,並在工作完成時排空。

回答

4

如果您在耗盡自動釋放池期間崩潰,那隻意味着您在該事件循環期間過度釋放了某處。如果同一個對象上有autorelease,那麼直到游泳池消失時纔會看到崩潰。這並不意味着autorelease與它有任何關係。那是剛剛發佈的最後一個版本。

確保您使用訪問器來訪問所有屬性(init和dealloc除外)。如果在非ARC代碼中崩潰,則直接訪問ivars是首要原因。無論如何,您需要審覈您對保留和釋放的平衡。轉移到ARC通常會減少這些類型,如果可能的話,強烈建議。

+0

感謝您的回答。是的,我意識到游泳池如何工作的機制。這裏的問題是我不知道視圖控制器如何進入autorelease池。它在主線程上分配,作爲僅分配屬性設置到操作上。控制器如何進入游泳池?我同意,轉移到ARC將是最終目標,這是......只是還沒有到那裏:) –

+0

對象總是進入游泳池。每次訪問一個原子屬性獲取器時,它都會獲取一個保留/自動釋放對。許多方法,尤其是處理線程安全的方法,都附加了額外的保留/自動釋放對。這是確保對象繼續存在直到方法結束的一種常用方法。一個常用的setter模式也是在設置新值之前自動釋放舊值。所以在autorelease池中顯示對象是很常見的,即使你沒有故意自動釋放​​它們。 –

+0

啊......這很好,謝謝。它解釋了爲什麼它在那裏,顯然它在這種情況下被過度釋放。好吧,現在找到罪魁禍首:P –

相關問題