Branch: refs/heads/main
  Home:   https://github.com/WebKit/WebKit
  Commit: d4b0840eea7761c9fa3184392d4c6659d60252e3
      
https://github.com/WebKit/WebKit/commit/d4b0840eea7761c9fa3184392d4c6659d60252e3
  Author: Sihui Liu <[email protected]>
  Date:   2026-08-11 (Tue, 11 Aug 2026)

  Changed paths:
    A 
LayoutTests/http/tests/site-isolation/draw-after-two-cross-process-navigations-expected.html
    A 
LayoutTests/http/tests/site-isolation/draw-after-two-cross-process-navigations.html
    A LayoutTests/http/tests/site-isolation/resources/red-background.html
    M Source/WebKit/UIProcess/RemoteLayerTree/RemoteLayerTreeHost.mm

  Log Message:
  -----------
  [Site Isolation] A destroyed hosted layer is left parented to its hosting 
layer
https://bugs.webkit.org/show_bug.cgi?id=321401
rdar://184468834

Reviewed by Alex Christensen.

RemoteLayerTreeHost::layerWillBeRemoved took the node out of m_nodes but never 
detached its layer, i.e. does not invoke
removeFromHostingNode. A CALayer is retained by its superlayer, so dropping the 
RemoteLayerTreeNode does not stop the
layer being drawn: the hosted root layer of a frame that has moved to another 
process stays parented to the hosting
layer and keeps compositing.

remotePageProcessDidTerminate already called removeFromHostingNode, bit it 
covered this for the process-termination path
only -- if the process is not destroyed when layer is removed, then no one is 
removing it from layer tree. This patch
fixes that by having RemoteLayerTreeHost::layerWillBeRemoved invoke 
removeFromHostingNode. By doing so, the call in
remotePageProcessDidTerminate becomes redundant.

The patch also contains two drive-by fixes for issues found in 
RemoteLayerTreeHost::layerWillBeRemoved:
- A LayerHostingContextIdentifier is reused across a frame's cross-process 
navigations, so it outlives the layers keyed
by it and an entry may already have been reassigned to a layer in another 
process (e.g. the new layer of the frame is
added before the the old layer is removed); clearing m_hostedLayers and 
m_hostingLayers by identifier alone could
therefore discard a live entry. Both removals now confirm that the entry still 
refers to the layer going away before
removal and update.
- When removing layer from m_hostedLayersInProcess, the key layerID is read 
from m_hostedLayers instead of using the
layerID parameter passed to the function. In the edge case mentioned above, the 
key stored in the map might already be
updated to new layer, and we will remove the new key by mistake. Now use 
function parameter as the key.
These two are races that no layout test can currently force.

Test: http/tests/site-isolation/draw-after-two-cross-process-navigations.html.

* 
LayoutTests/http/tests/site-isolation/draw-after-two-cross-process-navigations-expected.html:
 Added.
* 
LayoutTests/http/tests/site-isolation/draw-after-two-cross-process-navigations.html:
 Added.
* LayoutTests/http/tests/site-isolation/resources/red-background.html: Added. 
The regression test page is blue with a
200x200 iframe that navigates three times: a red page on localhost, a green 
page on a third site, and finally a URL on a
fourth site that responds with X-Frame-Options: deny, so a transparent document 
commits and nothing opaque is left to
hide a stale layer. The 1x1 #sibling frame is load-bearing: it is same-site 
with the red page, so that process stays
alive after the frame leaves it and reports the red layer as destroyed. Without 
it the process terminates instead and
takes the path that was already correct, and the test passes either way.
* Source/WebKit/UIProcess/RemoteLayerTree/RemoteLayerTreeHost.mm:
(WebKit::RemoteLayerTreeHost::layerWillBeRemoved):
(WebKit::RemoteLayerTreeHost::remotePageProcessDidTerminate):

Canonical link: https://commits.webkit.org/318978@main



To unsubscribe from these emails, change your notification settings at 
https://github.com/WebKit/WebKit/settings/notifications

Reply via email to