IntersectionObserver doesn't keep target's JS wrapper alive
authorajuma@chromium.org <ajuma@chromium.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 6 Nov 2018 20:52:51 +0000 (20:52 +0000)
committerajuma@chromium.org <ajuma@chromium.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Tue, 6 Nov 2018 20:52:51 +0000 (20:52 +0000)
commit48e578f0f5dd4aca7a8ee2a8d7358e708da48ef0
treed02c1761727630448f3786015e335de85d68cc77
parente25114b046edcc7d0849f0adbc864bdf9fb6387a
IntersectionObserver doesn't keep target's JS wrapper alive
https://bugs.webkit.org/show_bug.cgi?id=190235

Reviewed by Ryosuke Niwa.

Source/WebCore:

Retain JS wrappers of targets in queued entries using a vector of GCReachableRef owned by
IntersectionObserver, which gets cleared after the entries have been delivered.

Make IntersectionObserver::takeRecords return a struct which has both the vector of GCReachableRefs
for targets and the vector of intersection observer entries, so that the GCReachableRefs survive
until the creation of JS wrappers for the entries.

Modify IntersectionObserver::hasPendingActivity to keep the observer alive while it has
entries to deliver.

Tests: intersection-observer/intersection-observer-entry-keeps-js-wrapper-of-target-alive.html
       intersection-observer/intersection-observer-keeps-js-wrapper-of-target-alive.html
       intersection-observer/target-deleted.html

* Sources.txt:
* WebCore.xcodeproj/project.pbxproj:
* bindings/js/JSIntersectionObserverEntryCustom.cpp:
(WebCore::JSIntersectionObserverEntry::visitAdditionalChildren): Keep the target element's wrapper alive while the
IntersectionObserverEntry's wrapper is alive.
* page/IntersectionObserver.cpp:
(WebCore::IntersectionObserver::takeRecords): Change return type to include GCReachableRefs for each record's target, so that
each target can be kept until a JS wrapper is constructed for its IntersectionObserverEntry.
(WebCore::IntersectionObserver::appendQueuedEntry):
(WebCore::IntersectionObserver::notify): Erase GCReachableRefs for targets after delivering the corresponding records.
(WebCore::IntersectionObserver::hasPendingActivity const): Keep the IntersectionObserver alive until queued entries are delivered.
(WebCore::IntersectionObserver::stop):
* page/IntersectionObserver.h:
* page/IntersectionObserver.idl:
* page/IntersectionObserverEntry.h:
(WebCore::IntersectionObserverEntry::target const): Make this return a raw pointer instead of a RefPtr so that it
can be called in JSIntersectionObserverEntry::visitAdditionalChildren, which runs on the GC thread (it's illegal to ref a Node
on a non-main thread).
* page/IntersectionObserverEntry.idl:

LayoutTests:

Add test coverage.

Update test that depends on a target getting GC'd to call takeRecords() since
targets with pending entries are no logner GC'd.

* intersection-observer/intersection-observer-entry-keeps-js-wrapper-of-target-alive-expected.txt: Added.
* intersection-observer/intersection-observer-entry-keeps-js-wrapper-of-target-alive.html: Added.
* intersection-observer/intersection-observer-keeps-js-wrapper-of-target-alive-expected.txt: Added.
* intersection-observer/intersection-observer-keeps-js-wrapper-of-target-alive.html: Added.
* intersection-observer/root-element-deleted.html:
* intersection-observer/target-deleted-expected.txt: Added.
* intersection-observer/target-deleted.html: Added.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@237880 268f45cc-cd09-0410-ab3c-d52691b4dbfc
17 files changed:
LayoutTests/ChangeLog
LayoutTests/intersection-observer/intersection-observer-entry-keeps-js-wrapper-of-target-alive-expected.txt [new file with mode: 0644]
LayoutTests/intersection-observer/intersection-observer-entry-keeps-js-wrapper-of-target-alive.html [new file with mode: 0644]
LayoutTests/intersection-observer/intersection-observer-keeps-js-wrapper-of-target-alive-expected.txt [new file with mode: 0644]
LayoutTests/intersection-observer/intersection-observer-keeps-js-wrapper-of-target-alive.html [new file with mode: 0644]
LayoutTests/intersection-observer/root-element-deleted.html
LayoutTests/intersection-observer/target-deleted-expected.txt [new file with mode: 0644]
LayoutTests/intersection-observer/target-deleted.html [new file with mode: 0644]
Source/WebCore/ChangeLog
Source/WebCore/Sources.txt
Source/WebCore/WebCore.xcodeproj/project.pbxproj
Source/WebCore/bindings/js/JSIntersectionObserverEntryCustom.cpp [new file with mode: 0644]
Source/WebCore/page/IntersectionObserver.cpp
Source/WebCore/page/IntersectionObserver.h
Source/WebCore/page/IntersectionObserver.idl
Source/WebCore/page/IntersectionObserverEntry.h
Source/WebCore/page/IntersectionObserverEntry.idl