- From: Alexey Proskuryakov <ap@webkit.org>
- Date: Tue, 11 Nov 2008 23:44:42 +0300
Currently, HTML5 specifies that when a Document is discarded, "close" event should be asynchronously dispatched to MessagePorts that are entangled with ports belonging (in some specific sense) to this document. There is a race with garbage collection inherent to this requirement. Below I describe the issue in detail, and propose a solution. Suppose we have two browsing contexts, frameA and frameB, and two MessagePorts, portA and portB, owned by these contexts respectively. The ports are entangled with each other, and their queues are started. Further, portA is not reachable from live code, but has a "close" event listener (set via either onclose or addEventListener). Port portB is also unreachable, so garbage collection can destroy both ports. Now, we close frameB. This results in its document being discarded, so a "close" event is dispatched on portA (portA becomes GC protected when the task to dispatch it is posted). However, no event is dispatched if portA and portB are collected before the document is destroyed. The problem is that observable behavior depends on GC order, which it shouldn't. In practice, it is normally the same GC pass that destroys the Document and both unreachable ports, so a straightforward implementation is likely to crash due to using semi-deleted objects. I propose to remove the requirement to dispatch "close" event on the surviving port (#3 in paragraph 7.5.3.1). This is the only fix I can see, as making GC dispatch "close" to fix it from other side would suffer from basically the same logical problem. - WBR, Alexey Proskuryakov.
Received on Tuesday, 11 November 2008 12:44:42 UTC