欧美free性护士vide0shd,老熟女,一区二区三区,久久久久夜夜夜精品国产,久久久久久综合网天天,欧美成人护士h版

首頁綜合 正文
目錄

柚子快報激活碼778899分享:iOS崩潰監(jiān)控

柚子快報激活碼778899分享:iOS崩潰監(jiān)控

http://yzkb.51969.com/

目錄

關于集中常見的崩潰場景

發(fā)散思維

UI更新一定要在UI線程里實現(xiàn)的原因

崩潰問題分類

信號可捕獲崩潰

信號不可捕獲崩潰

崩潰日志捕獲

信號可捕獲崩潰

利用Xcode

第三方工具

捕獲原理

信號不可捕獲崩潰

后臺任務超時崩潰

后臺任務超時崩潰原因

如何捕獲后臺崩潰呢?

其他崩潰

采集到崩潰信息后如何分析并解決崩潰問題

總結

關于集中常見的崩潰場景

數(shù)組越界:在取數(shù)據(jù)索引時越界,App 會發(fā)生崩潰。還有一種情況,就是給數(shù)組添加了 nil 會崩潰。多線程問題:在子線程中進行 UI 更新可能會發(fā)生崩潰(不一定都會崩潰,但不建議在其他線程更新UI,這是一個約定俗成的規(guī)則)。多個線程進行數(shù)據(jù)的讀取操作,因為處理時機不一致,比如有一個線程在置空數(shù)據(jù)的同時另一個線程在讀取這個數(shù)據(jù),可能會出現(xiàn)崩潰情況。主線程無響應:如果主線程超過系統(tǒng)規(guī)定的時間無響應,就會被 Watchdog 殺掉。這時,崩潰問題對應的異常編碼是 0x8badf00d。關于這個異常編碼,我還會在后文和你說明。野指針:指針指向一個已刪除的對象訪問內(nèi)存區(qū)域時,會出現(xiàn)野指針崩潰。野指針問題是需要我們重點關注的,因為它是導致 App 崩潰的最常見,也是最難定位的一種情況。

發(fā)散思維

UI更新一定要在UI線程里實現(xiàn)的原因

1.UI控件操作不加鎖:為其加鎖則會耗費大量資源并拖慢運行速度

????????目的在于提高移動端更新UI的效率(對于UI控件的操作不加鎖)和和安全性(都在UI線程操作即加了所謂“偽鎖”),以此帶來流暢的體驗。原因是:

????????移動端(安卓和iOS)的UI訪問是沒有加鎖的,多個線程可以同時訪問更新操作同一個UI控件。也就是說訪問UI的時候,系統(tǒng)當中的控件都不是線程安全的,這將導致在多線程模式下,當多個線程共同訪問更新操作同一個UI控件時容易發(fā)生不可控的錯誤,而這是致命的。所以規(guī)定只能在UI線程中訪問UI,這相當于從另一個角度給移動端的UI訪問加上鎖,一個偽鎖。

????????多線程處理UI并沒有給我們開發(fā)帶來更多的便利,假如你代入了這些情景進行思考,你很容易得出一個結論: “我在一個串行隊列對這些事件進行處理就可以了?!?蘋果也是這樣想的,所以UIKit的所有操作都要放到主線程串行執(zhí)行。

2.整個程序的起點UIApplication是在主線程進行初始化,所有的用戶事件都是在主線程上進行傳遞(如點擊、拖動),所以view只能在主線程上才能對事件進行響應

3.在渲染方面由于圖像的渲染需要以60幀的刷新率在屏幕上 同時 更新,在非主線程異步化的情況下無法確定這個處理過程能夠?qū)崿F(xiàn)同步更新

崩潰問題分類

信號可捕獲崩潰

KVO問題

添加了觀察者,但未實現(xiàn) observeValueForKeyPath:ofObject:change:context: 方法,導致崩潰。(觀察者必須遵循的協(xié)議,不符合規(guī)矩的觀察則)觀察者對象dealloc了,但是沒有removeKVO多次removeKVO添加和remove的次數(shù)不一致添加或者移除時 keypath == nil,導致崩潰。

? ? ? ? 防護方法:

????????通過runtime特性對addObserver:forKeyPath:options:context:、removeObserver:forKeyPath:方法做替換,避免下面幾種情況: ????????添加觀察者時:通過關系哈希表判斷是否重復添加,只添加一次。 ????????移除觀察者時:通過關系哈希表是否已經(jīng)進行過移除操作,避免多次移除。 ????????觀察鍵值改變時:同樣通過關系哈希表判斷,將改變操作分發(fā)到原有的觀察者上。 ????????詳細介紹參考:?https://juejin.im/post/6844903927469588488?

NSNotification線程問題

在主線程發(fā)送通知注意不要多次添加數(shù)組越界野指針

信號不可捕獲崩潰

后臺任務超時內(nèi)存打爆主線程卡頓超閾值

崩潰日志捕獲

信號可捕獲崩潰

利用Xcode

????????就是打開 Xcode 的菜單選擇 Product -> Archive。然后,在提交時選上“Upload your app’s symbols to receive symbolicated reports from Apple”,以后你就可以直接在 Xcode 的 Archive 里看到符號化后的崩潰日志了。

第三方工具

????????但是這種查看日志的方式,每次都是純手工的操作,而且時效性較差。所以,目前很多公司的崩潰日志監(jiān)控系統(tǒng),都是通過PLCrashReporter 這樣的第三方開源庫捕獲崩潰日志,然后上傳到自己服務器上進行整體監(jiān)控的。而沒有服務端開發(fā)能力,或者對數(shù)據(jù)不敏感的公司,則會直接使用 Fabric或者Bugly來監(jiān)控崩潰。

捕獲原理

// 表示的是,EXC_BAD_ACCESS 這個異常會通過 SIGSEGV 信號發(fā)現(xiàn)有問題的線程。

Exception Type: EXC_BAD_ACCESS (SIGSEGV)

// 雖然信號的種類有很多,但是都可以通過注冊 signalHandler 來捕獲到。其實現(xiàn)代碼,如下所示:

void registerSignalHandler(void) {

signal(SIGSEGV, handleSignalException);

signal(SIGFPE, handleSignalException);

signal(SIGBUS, handleSignalException);

signal(SIGPIPE, handleSignalException);

signal(SIGHUP, handleSignalException);

signal(SIGINT, handleSignalException);

signal(SIGQUIT, handleSignalException);

signal(SIGABRT, handleSignalException);

signal(SIGILL, handleSignalException);

}

void handleSignalException(int signal) {

NSMutableString *crashString = [[NSMutableString alloc]init];

void* callstack[128];

int i, frames = backtrace(callstack, 128);

char** traceChar = backtrace_symbols(callstack, frames);

for (i = 0; i

[crashString appendFormat:@"%s\n", traceChar[i]];

}

NSLog(crashString);

}

????????上面這段代碼對各種信號都進行了注冊,捕獲到異常信號后,在處理方法 handleSignalException 里通過 backtrace_symbols 方法就能獲取到當前的堆棧信息。

????????堆棧信息可以先保存在本地,下次啟動時再上傳到崩潰監(jiān)控服務器就可以了。先將捕獲到的堆棧信息保存在本地,是為了實現(xiàn)堆棧信息數(shù)據(jù)的持久化存儲。

????????那么,為什么要實現(xiàn)持久化存儲呢?這是因為,在保存完這些堆棧信息以后,App 就崩潰了,崩潰后內(nèi)存里的數(shù)據(jù)也就都沒有了。而將數(shù)據(jù)保存在本地磁盤中,就可以在 App 下次啟動時能夠很方便地讀取到這些信息。

? ? ? ? 問題:使用 registerSignalHandler 和handleSignalHandler 是能夠捕獲到異常。 但是,這個時候 app 已經(jīng)立即要 crash 了。捕獲的異常怎么才能確保能夠持久化到沙盒呢?寫入文件的代碼是沒法保證在 crash 前正常執(zhí)行完的吧!

? ? ? ? 答案:寫入數(shù)據(jù)的時候 - (void)performSelectorOnMainThread:(SEL)aSelector withObject:(nullable id)arg waitUntilDone:(BOOL)wait; waitUntilDone 設置為YES 就是主線程同步執(zhí)行 執(zhí)行完才會崩潰

????????思考:是否還有其他方式?

信號不可捕獲崩潰

后臺任務超時崩潰

后臺任務超時崩潰原因

? ? ? ? 后臺崩潰原因?先來看下后臺?;?種方式

Background Task 方式,是使用最多的。App 退后臺后,默認都會使用這種方式。使用 Background Mode 方式的話,App Store 在審核時會提高對 App 的要求。通常情況下,只有那些地圖、音樂播放、VoIP 類的 App 才能通過審核。Background Fetch 方式的喚醒時間不穩(wěn)定,而且用戶可以在系統(tǒng)里設置關閉這種方式,導致它的使用場景很少。Silent Push 是推送的一種,會在后臺喚起 App 30 秒。它的優(yōu)先級很低,會調(diào)用 application:didReceiveRemoteNotifiacation:fetchCompletionHandler: 這個 delegate,和普通的 remote push notification 推送調(diào)用的 delegate 是一樣的。PushKit 后臺喚醒 App 后能夠?;?30 秒。它主要用于提升 VoIP 應用的體驗。

????????Background Task 方式為什么是使用最多的,它可以解決哪些問題?在你的程序退到后臺以后,只有幾秒鐘(大概10s)的時間可以執(zhí)行代碼,接下來就會被系統(tǒng)掛起。進程掛起后所有線程都會暫停,不管這個線程是文件讀寫還是內(nèi)存讀寫都會被暫停。但是,數(shù)據(jù)讀寫過程無法暫停只能被中斷,中斷時數(shù)據(jù)讀寫異常而且容易損壞文件,所以系統(tǒng)會選擇主動殺掉 App 進程。

????????而 Background Task 這種方式,就是系統(tǒng)提供了 beginBackgroundTaskWithExpirationHandler 方法來延長后臺執(zhí)行時間,可以解決你退后臺后還需要一些時間去處理一些任務的訴求。

- (void)applicationDidEnterBackground:(UIApplication *)application {

self.backgroundTaskIdentifier = [application beginBackgroundTaskWithExpirationHandler:^( void) {

[self yourTask];

}];

}

????????如果 yourTask 在 3 分鐘之內(nèi)沒有執(zhí)行完的話,系統(tǒng)會強制殺掉進程,從而造成崩潰,這就是為什么 App 退后臺容易出現(xiàn)崩潰的原因。

如何捕獲后臺崩潰呢?

????????怎么去收集退后臺后超過?;铋撝刀鴮е滦盘柌东@不到的那些崩潰信息呢?

????????采用 Background Task 方式時,我們可以根據(jù) beginBackgroundTaskWithExpirationHandler 會讓后臺?;?3 分鐘這個閾值,先設置一個計時器,在接近 3 分鐘時判斷后臺程序是否還在執(zhí)行。如果還在執(zhí)行的話,我們就可以判斷該程序即將后臺崩潰,進行上報、記錄,以達到監(jiān)控的效果。(也就是判斷后臺任務執(zhí)行是否超過閾值)

其他崩潰

????????其他捕獲不到的崩潰情況還有很多,主要就是內(nèi)存打爆和主線程卡頓時間超過閾值被 watchdog 殺掉這兩種情況。

????????其實,監(jiān)控這兩類崩潰的思路和監(jiān)控后臺崩潰類似,我們都先要找到它們的閾值,然后在臨近閾值時還在執(zhí)行的后臺程序,判斷為將要崩潰,收集信息并上報。

采集到崩潰信息后如何分析并解決崩潰問題

????????我們采集到的崩潰日志,主要包含的信息為:進程信息、基本信息、異常信息、線程回溯。

進程信息:崩潰進程的相關信息,比如崩潰報告唯一標識符、唯一鍵值、設備標識;基本信息:崩潰發(fā)生的日期、iOS 版本;異常信息:異常類型、異常編碼、異常的線程;線程回溯:崩潰時的方法調(diào)用棧

????????通常情況下,我們分析崩潰日志時最先看的是異常信息,分析出問題的是哪個線程,在線程回溯里找到那個線程;然后,分析方法調(diào)用棧,符號化后的方法調(diào)用??梢酝暾乜吹椒椒ㄕ{(diào)用的過程,從而知道問題發(fā)生在哪個方法的調(diào)用上。

????????一些被系統(tǒng)殺掉的情況,我們可以通過異常編碼來分析。你可以在維基百科上,查看完整的異常編碼。這里列出了 44 種異常編碼,但常見的就是如下三種:

0x8badf00d,表示 App 在一定時間內(nèi)無響應而被 watchdog 殺掉的情況。0xdeadfa11,表示 App 被用戶強制退出。0xc00010ff,表示 App 因為運行造成設備溫度太高而被殺掉。

????????除了崩潰日志外,崩潰監(jiān)控平臺還需要對所有采集上來的日志進行統(tǒng)計。我以騰訊的 Bugly 平臺為例,和你一起看一下崩潰監(jiān)控平臺一般都會記錄哪些信息,來輔助開發(fā)者追溯崩潰問題。

總結

????????現(xiàn)有的崩潰監(jiān)控系統(tǒng),不管是開源的崩潰日志收集庫還是類似 Bugly 的崩潰監(jiān)控系統(tǒng),離最優(yōu)解都還有一定的距離。

????????這個“非最優(yōu)”,我們需要分兩個維度來看:一個維度是,怎樣才能夠讓崩潰信息的收集效率更高,丟失率更低;另一個維度是,如何能夠收集到更多的崩潰信息,特別是系統(tǒng)強殺帶來的崩潰。

????????隨著 iOS 系統(tǒng)的迭代更新,強殺閾值和強殺種類都在不斷變化,因此崩潰監(jiān)控系統(tǒng)也需要跟上系統(tǒng)迭代更新的節(jié)奏,同時還要做好向下兼容。

柚子快報激活碼778899分享:iOS崩潰監(jiān)控

http://yzkb.51969.com/

推薦閱讀

評論可見,查看隱藏內(nèi)容

本文內(nèi)容根據(jù)網(wǎng)絡資料整理,出于傳遞更多信息之目的,不代表金鑰匙跨境贊同其觀點和立場。

轉(zhuǎn)載請注明,如有侵權,聯(lián)系刪除。

本文鏈接:http://m.gantiao.com.cn/post/18874108.html

發(fā)布評論

您暫未設置收款碼

請在主題配置——文章設置里上傳

掃描二維碼手機訪問

文章目錄