We currently have a lot of code for firing load/error events spread across a lot of different areas that makes it very hard to reason about.
- For firing load to the <iframe> element:
nsDocumentViewer::LoadComplete fires a load event for the inner document if the load was a success. We have a TODO here for also firing an error event, but note that this would only run if the load got far enough to create a document viewer.
nsGlobalWindowInner::PostHandleEvent catches the load event, and forwards it to the embedder with FireFrameLoadEvent. If we are an out of process iframe, then this also sends it across IPC to the embedder, and unblocks the load event of the outer document.
- For firing error to the <iframe> element:
This is fired by nsFrameLoader::FireErrorEvent. It's only called for errors that we synchronously detect, so doesn't ever fire for OOP iframes, loads that go through Document::InitializeFrameLoader, or for errors returned asynchronously from the channel within docshell.
It's hard to know exactly which set of possible errors this is, and how it's being changed by fission moving more <iframe>s OOP.
- Unblocking the load event (for the Document) when an OOP iframe finishes loading:
When the inner Document finishes loading, we call BrowserChild::SendMaybeFireEmbedderLoadEvents to notify the outer Document. When this happens from the nsGlobalWindowInner callsite, it also acts as the way we request the load event to be fired on the <iframe> element.
There are callers to this function spread across nsDocShell, nsDocLoader and nsGlobalWindowInner. These are trying to catch every possible case in which loading might be done, and frequently we hit multiple of them for a single load (which is safe, but a bit weird).
It seems like we'd ideally have a single owner for knowing when loading is complete, and then we can have clear decision making on which events to fire (and for which error code types).
I suspect we're not firing error anywhere near as much as we should (and this is changing with fission), but I think we need to clean this up before we can make much progress on figuring out exactly which failure types need an error event.