在 Windows 上,記憶體不足曾是 Firefox 最大的當機來源——然而許多受影響的使用者其實還有數 GB 的實體記憶體閒置。Windows 會限制應用程式可 commit 的記憶體量,上限為 RAM 加上置換檔大小,而 Firefox 無法控制所有消耗該「commit space」的來源:顯示驅動程式會為紋理 commit 記憶體,這些記憶體鮮少使用,卻仍計入上限。Firefox 多年來持續精簡自身的記憶體用量並監控效能退步,但這些努力都未能像最終的訣竅那樣改變當機率。

面對無法滿足的配置請求,慣常做法是放棄:大多數失敗路徑都沒有合理的續行方式,因此瀏覽器會以受控方式當機。這種做法把 commit space 上限視為固定不變,但在 Windows 上並非如此——當置換檔幾乎滿載時,作業系統會自動將其擴大,增加應用程式可 commit 的記憶體量。

Mozilla 的做法是讓主程序在配置失敗時短暫等待,然後重試,給 Windows 時間擴大分頁檔。這段停頓還帶來另一項好處:Firefox 以多個程序執行,除了主程序之外,失去任何一個程序都能存活,因此在延遲期間,記憶體失控的內容程序或 GPU 程序往往會先死亡,騰出空間讓瀏覽器繼續運作。失去一個網頁或看到短暫閃爍,勝過整個瀏覽器當機。

這項技巧隨 Firefox 105 推出,使每活躍使用小時的記憶體不足瀏覽器當機減少超過 70%——遠超 Mozilla 最樂觀的預測。團隊曾在 Android 版 Firefox 與 Firefox OS 上成功運用相同做法,而在記憶體壓力下分頁當機略微上升,則是他們接下來著手減少的目標。

在 Windows 上,配置失敗未必致命——作業系統會視需求擴大分頁檔,因此等待並重試能將記憶體不足當機轉化為短暫停頓。

Windows 不會殺死配置失敗的應用程式——該呼叫會傳回錯誤,因此程序可以選擇等待並重試,而非直接死亡。

commit space 上限可以擴大:當置換檔幾乎滿載時,Windows 會自動擴增,而短暫的暫停正好給它時間這麼做。

Firefox 的多程序設計意味著,停頓主程序可讓可重新載入的內容程序或 GPU 程序先死亡並釋放記憶體,從而保護整個瀏覽器。

這項變更改變的是失敗處理方式,而非記憶體用量,這正是為何一個小修正能勝過多年來的記憶體足跡精簡。

當平台能視需求擴充資源時,應暫停而非在失敗時當機——而在多程序應用程式中,讓可重新載入的子程序先承受損害。

Firefox 105 於 2022 年 9 月推出等待後重試的行為,遙測顯示每活躍使用小時的記憶體不足瀏覽器當機減少超過 70%——「遠超我們最樂觀的預測」。這段停頓造成分頁當機小幅上升,團隊隨後著手減少,而 Mozilla 也開始區分 commit space 不足與實體記憶體不足,讓 Firefox 能採取不同因應並減少置換。工程師 Raymond Kraesig 實作了這項技巧並監控其影響;相同技術早已在 Android 版 Firefox 與 Firefox OS 上奏效。

追溯依據

參考來源

  1. Improving Firefox stability with this one weird trick Mozilla Hacks · hacks.mozilla.org ·
  2. Hacker News discussion: Improving Firefox stability with this one weird trick Hacker News · news.ycombinator.com ·