macOS 如何報告錯誤訊息

當應用程式或軟體當機,「Crash Reporter(當機報告)」會告訴你哪些地方出了問題。但在最近的 macOS 版本中,這份「報告」已被另外一個較為複雜的「Problem Reporter」所取代,該程序位在系統資料夾的卷宗裡(/System/Library/CoreServices),且在介面上執行,這不同於「kernel panics(內核當機)」,他們的運作方式非常不同,內核當機會自動重新開機,接著會顯示錯誤訊息在畫面上。

當機報告有一段起起伏伏的過去,幾年前,Apple 在 macOS 的更新中釋出了一個有瑕疵的應用程式,這不僅會讓程式本身出現問題,而哪怕只是簡單的程式,也很有可能會造成系統全面性的當機。

當機報告現在主要依賴兩種程式,分別是「CrashHandler」、及「ReportCrash」,一個用於 root,另一個則用於使用者,使用者的部分則會根據 Property Lists(屬性列表)來啟動當機報告:

  • /System/Library/LaunchAgents for the user ReportCrash
  • /System/Library/LaunchDemons for the root ReportCrash com.apple.ReportCrash.Root.plist

而另一個 LaunchDaemon 系統則負責啟動 CrashReporterSupportHelper,根據以下這些檔案裡的元件來決定是否需要啟動:

  • /System/Library/CoreServices/ReportCrash
  • /System/Library/CoreServices/CrashReporterSupportHelper
  • /System/Library/CoreServices/Problem Reporter.app

而這些屬性列表都會被儲存在系統的卷宗裡,是不能被移除或更改的。

但奇怪的是,當機報告有一部分的行為卻仍然取決於它前身的檔案,它位在 ~/Library/Preferences/com.apple.CrashReporter.plist,這個可以透過預設的指令工具來更改,但目前似乎只有兩種偏好選項可以設定。有個名為 com.apple.ProblemReporter.plist 的檔案,是用來儲存視窗大小、位置及介面等相關的配置。

而預設的 LogCrashes = YES,則是將當機的 log 寫入傳統的 log 檔中,可以在當機報告中的 Console 查看(路徑為 ~/Library/Preferences/com.apple.CrashReporter.plist),而 UseUNE = 0 的設定更為有用,正如 Guilherme Rambo @_inside 所指出的那樣,若將 0 改為 1,則當機報告將會從原本預設的互動視窗(對話窗)改為通知。

而這是將 UseUNC 改為 1 時,通知的樣式顯示在視窗的右下角,然後你可以點擊查看預設的視窗,也可用以下的指令列來使用「通知」的形式而不是互動視窗。

defaults write com.apple.CrashReporter UseUNC 1

Apple 還曾經提出一個名為 CrashReporterPrefs.app 的 Xcode 應用程式,它可以改變當機報告的偏好設定,但那已經過時了,更別說想要將程式開啟了。

在以前,你可以關閉當機報告,但現在,它已經被鎖定在系統的卷宗裡,當然,你還是可以使用指令工具來禁用這個功能。

  • launchctl unload -w /System/Library/LaunchAgents/com.apple.ReportCrash.plist
  • sudo launchctl unload -w /System/Library/LaunchDaemons/com.apple.ReportCrash.Root.plist

你可以使用以下兩行指令列來恢復當機的報告:

  • launchctl load -w /System/Library/LaunchAgents/com.apple.ReportCrash.plist
  • sudo launchctl load -w /System/Library/LaunchDaemons/com.apple.ReportCrash.Root.plist

注意:上述測試不確定在 macOS Monterey 中是否可行。

當機報告

儘管 Apple 為使用者提供有關問題報告的相關資訊很少,但當機報告已經被廣泛紀錄,主網頁亦提供了文件予以說明:

實際上,除非當機報告的程式是你寫的,否則你很難在當機報告中解釋任何導致當機的原因,特別是一般使用者,但是,報告中的資訊對所有開發人員來說卻是非常珍貴的訊息,因為他們可以透過這些資訊來修復當機的狀況,進而改善他們的應用程式或軟體。

但某些時候,報告中的提示對使用者來說還是有意義的,比如說下面這個例子:

Incident Identifier: 71383068-FEF5-422C-AC90-21B8CED55EED
CrashReporter Key: E29803D9-C348-491D-3236-CFF765A4E549
Hardware Model: iMacPro1,1
Process: Signet [90704]
Path: /Users/USER/Documents/*/SignetTest1.app/Contents/MacOS/Signet
Identifier: co.eclecticlight.Signet
Version: 1.0b1 (1)
Code Type: X86-64 (Native)
Role: Default
Parent Process: launchd [1]
Coalition: co.eclecticlight.Signet [94569]

Exception Type: EXC_CRASH (SIGKILL (Code Signature Invalid))
Exception Codes: 0x0000000000000000, 0x0000000000000000
Exception Note: EXC_CORPSE_NOTIFY
Termination Reason: CODESIGNING 1

EOF

透過這個例子,我們就可以知道,該應用程式發生錯誤的原因是因為它的簽署是無效的。

你的下一步

TWDC 提供 macOS IT 人員相關學習課程,進一步了解 macOS 安全防護科技。或歡迎與我們諮詢  macOS 相關的終端防護軟體。

原文連結:https://eclecticlight.co/2021/12/10/how-macos-reports-crashes/