Backend handoff reworked for remote ImageBuffers
Component: WebKit GPU Process / Remote Rendering | 1a3eac1
Accelerated canvas and WebGL rendering is split across processes: the WebProcess holds a RemoteImageBufferProxy while the actual pixel backing store — often a GPU-backed IOSurface — lives in the GPU process behind RemoteRenderingBackend and RemoteImageBuffer, with IPC keeping the two synchronized. IOSurfaces are pooled and recycled for performance, so any code path holding a live reference to one — including transferring its handle to the WebProcess — prevents reuse.
Previously, every new GPU-process-backed ImageBuffer sent its backend handle to the WebProcess on creation as an async DidCreateBackend message, and RemoteImageBufferProxy started backend-less, blocking dependent operations until that message arrived. This commit replaces that handshake: the backend is instantiated at creation time, and the underlying handle is fetched synchronously only when a caller actually needs it — which is now just PlaceholderRenderingContext and view transitions.
Before: After:
create ImageBuffer create ImageBuffer
└─► GPU: build backend └─► GPU: build backend (eager)
└─► async DidCreateBackend proxy usable immediately
└─► WebProcess gets handle
▲ pins IOSurface handle fetched synchronously
defeats pool only by the two consumers
▲ callers must that need it
drain the message
Significance
Eagerly shipping handles to the WebProcess on every buffer creation pinned IOSurfaces and defeated the IOSurfacePool, causing alloc/dealloc churn under tight self-drawImage() loops on accelerated 2D canvas. Beyond the performance fix, this removes an entire class of async IPC handshake that callers previously had to explicitly drain — a state machine where an object exists but is not yet usable is a recurring source of ordering bugs, and that state no longer exists here.