Concurrent GC should be able to run splay in debug mode and earley/raytrace in releas...
authorfpizlo@apple.com <fpizlo@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 18 Nov 2016 22:11:51 +0000 (22:11 +0000)
committerfpizlo@apple.com <fpizlo@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 18 Nov 2016 22:11:51 +0000 (22:11 +0000)
commita301b34a331755cb4044930e89cece3de65017ca
tree520096d37209560c795b9bd46a76a4056d8a1977
parent6bb791e083555fc539d0d5dedab8f2faa320a6fb
Concurrent GC should be able to run splay in debug mode and earley/raytrace in release mode with no perf regression
https://bugs.webkit.org/show_bug.cgi?id=164282

Reviewed by Geoffrey Garen and Oliver Hunt.

PerformanceTests:

CDjs is a fun benchmark for stressing concurrent GCs, but to really give the GC a good
workout you need to increase the amount of work that the test does. This adds a second
configuration of the benchmark that has more aircraft. It uses much more memory and causes us
to do more GCs and those GCs take longer.

* JetStream/cdjs/benchmark.js:
(benchmarkImpl):
(benchmark):
* JetStream/cdjs/large.js: Added.

Source/JavaScriptCore:

The two three remaining bugs were:

- Improper ordering inside putDirectWithoutTransition() and friends. We need to make sure
  that the GC doesn't see the store to Structure::m_offset until we've resized the butterfly.
  That proved a bit tricky. On the other hand, this means that we could probably remove the
  requirement that the GC holds the Structure lock in some cases. I haven't removed that lock
  yet because I still think it might protect some weird cases, and it doesn't seem to cost us
  anything.

- CodeBlock's GC strategy needed to be made thread-safe (visitWeakly, visitChildren, and
  their friends now hold locks) and incremental-safe (we need to update predictions in the
  finalizer to make sure we clear anything that was put into a value profile towards the end
  of GC).

- The GC timeslicing scheduler needed to be made a bit more aggressive to deal with
  generational workloads like earley, raytrace, and CDjs. Once I got those benchmarks to run,
  I found that they would do many useless iterations of GC because they wouldn't pause long
  enough after rescanning weak references and roots. I added a bunch of knobs for forcing a
  pause. In the end, I realized that I could get the desired effect by putting a ceiling on
  mutator utilization. We want the GC to finish quickly if it is possible to do so, even if
  the amount of allocation that the mutator had done is low. Having a utilization ceiling
  seems to accomplish this for benchmarks with trivial heaps (earley and raytrace) as well as
  huge heaps (like CDjs in its "large" configuration).

This preserves splay performance, makes the concurrent GC more stable, and makes the
concurrent GC not a perf regression on earley or raytrace. It seems to give us great CDjs
performance as well, but this is still hard to tell because we crash a lot in that benchmark.

* bytecode/CodeBlock.cpp:
(JSC::CodeBlock::CodeBlock):
(JSC::CodeBlock::visitWeakly):
(JSC::CodeBlock::visitChildren):
(JSC::CodeBlock::shouldVisitStrongly):
(JSC::CodeBlock::shouldJettisonDueToOldAge):
(JSC::CodeBlock::propagateTransitions):
(JSC::CodeBlock::determineLiveness):
(JSC::CodeBlock::WeakReferenceHarvester::visitWeakReferences):
(JSC::CodeBlock::UnconditionalFinalizer::finalizeUnconditionally):
(JSC::CodeBlock::visitOSRExitTargets):
(JSC::CodeBlock::stronglyVisitStrongReferences):
(JSC::CodeBlock::stronglyVisitWeakReferences):
* bytecode/CodeBlock.h:
(JSC::CodeBlock::clearVisitWeaklyHasBeenCalled):
* heap/CodeBlockSet.cpp:
(JSC::CodeBlockSet::deleteUnmarkedAndUnreferenced):
* heap/Heap.cpp:
(JSC::Heap::ResumeTheWorldScope::ResumeTheWorldScope):
(JSC::Heap::markToFixpoint):
(JSC::Heap::beginMarking):
(JSC::Heap::addToRememberedSet):
(JSC::Heap::collectInThread):
* heap/Heap.h:
* heap/HeapInlines.h:
(JSC::Heap::mutatorFence):
* heap/MarkedBlock.cpp:
* runtime/JSCellInlines.h:
(JSC::JSCell::finishCreation):
* runtime/JSObjectInlines.h:
(JSC::JSObject::putDirectWithoutTransition):
(JSC::JSObject::putDirectInternal):
* runtime/Options.h:
* runtime/Structure.cpp:
(JSC::Structure::add):
* runtime/Structure.h:
* runtime/StructureInlines.h:
(JSC::Structure::add):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@208897 268f45cc-cd09-0410-ab3c-d52691b4dbfc
17 files changed:
PerformanceTests/ChangeLog
PerformanceTests/JetStream/cdjs/benchmark.js
PerformanceTests/JetStream/cdjs/large.js [new file with mode: 0644]
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/bytecode/CodeBlock.cpp
Source/JavaScriptCore/bytecode/CodeBlock.h
Source/JavaScriptCore/heap/CodeBlockSet.cpp
Source/JavaScriptCore/heap/Heap.cpp
Source/JavaScriptCore/heap/Heap.h
Source/JavaScriptCore/heap/HeapInlines.h
Source/JavaScriptCore/heap/MarkedBlock.cpp
Source/JavaScriptCore/runtime/JSCellInlines.h
Source/JavaScriptCore/runtime/JSObjectInlines.h
Source/JavaScriptCore/runtime/Options.h
Source/JavaScriptCore/runtime/Structure.cpp
Source/JavaScriptCore/runtime/Structure.h
Source/JavaScriptCore/runtime/StructureInlines.h