There are three main reasons for making Firefox run content in a separate process: performance, security, and stability.
Performance
Most performance work at Mozilla over the last two years has focused on responsiveness of the browser. The goal is to reduce “jank”—those times when the browser seems to briefly freeze when loading a big page, typing in a form, or scrolling. Responsiveness tends to matter a lot more than throughput on the web today. Much of this work has been done as part of the Snappy project. The main focuses have been:
- Moving long-running actions to a separate thread so that the main thread can continue to respond to the user.
- Doing I/O asynchronously or on other threads so that the main thread isn’t blocked waiting for the disk.
- Breaking long-running code into shorter pieces and running the event loop in between. Incremental garbage collection is an example of this.
Much of the low-hanging fruit in these areas has already been picked. The remaining issues are difficult to fix. For example, JavaScript execution and layout happen on the main thread, and they block the event loop. Running these components on a separate thread is difficult because they access data, like the DOM, that are not thread-safe. As an alternative, we’ve considered allowing the event loop to run in the middle of JavaScript execution, but doing so would break a lot of assumptions made by other parts of Firefox (not to mention add-ons).
Running web content in a separate process is a nice alternative to these approaches. Like the threaded approach, Firefox is able to run its event loop while JavaScript and layout are running in a content process. But unlike threading, the UI code has no access to content DOM or or other content data structures, so there is no need for locking or thread-safety. The downside, of course, is that any code in the Firefox UI process that needs to access content data must do so explicitly through message passing.
We feel this tradeoff makes sense for a few reasons:
- It’s not all that common for Firefox code to access content DOM.
- Code that is shared with Firefox OS already uses message passing.
- In the multiprocess model, Firefox code that fails to use message passing to access content will fail in an obvious, consistent way. In the threaded model, code that accesses content without proper locking will fail in subtle ways that are difficult to debug.
Security
Right now, if someone discovers an exploitable bug in Firefox, they’re able to take over users’ computers. There are a lot of techniques to mitigate this problem, but one of the most powerful is sandboxing. Technically, sandboxing doesn’t require multiple processes. However, a sandbox that covered single-process Firefox wouldn’t be very useful. Sandboxes are only able to prevent processes from performing actions that a well-behaved process would never do. Unfortunately, a well-behaved Firefox process (especially one with add-ons installed) needs access to much of the network and file system. Consequently, a sandbox for single-process Firefox couldn’t restrict much.
In multiprocess Firefox, content processes will be sandboxed. A well-behaved content process won’t access the filesystem directly; it will have to ask the main process to perform the request. At that time, the main process can verify that the request is safe and that it makes sense. Consequently, the sandbox for content processes can be quite restrictive. Our hope is that this arrangement will make it much harder to craft exploitable security holes for Firefox.
Stability
Currently, a crash in the code running a web page will take down the entire browser. With multiprocess Firefox, only the content process that crashed will be killed.
This page incorporates a lot of content from Bill McCloskey's blog post on multiprocess Firefox: https://billmccloskey.wordpress.com/2013/12/05/multiprocess-firefox/