Branch: refs/heads/main
  Home:   https://github.com/WebKit/WebKit
  Commit: 3d1bebd7930d04331a2a38714085dca3a0bdaf51
      
https://github.com/WebKit/WebKit/commit/3d1bebd7930d04331a2a38714085dca3a0bdaf51
  Author: Yusuke Suzuki <[email protected]>
  Date:   2026-06-01 (Mon, 01 Jun 2026)

  Changed paths:
    A JSTests/microbenchmarks/array-iterator-fast-entries.js
    A JSTests/microbenchmarks/array-iterator-fast-keys.js
    A JSTests/microbenchmarks/array-iterator-fast-values.js
    A JSTests/stress/array-iterator-fast-cross-realm.js
    A JSTests/stress/array-iterator-fast-ftl.js
    A 
JSTests/stress/array-iterator-fast-iterator-proto-symbol-iterator-overridden.js
    A JSTests/stress/array-iterator-fast-keys-values-entries.js
    A JSTests/stress/array-iterator-fast-mid-iteration.js
    A JSTests/stress/array-iterator-fast-multi-mode-cross-realm-prototype.js
    A JSTests/stress/array-iterator-fast-non-array-iterated-object.js
    A JSTests/stress/array-iterator-fast-own-symbol-iterator-on-instance.js
    A JSTests/stress/array-iterator-fast-watchpoint-invalidate-next.js
    A 
JSTests/stress/array-iterator-fast-watchpoint-invalidate-symbol-iterator.js
    A 
JSTests/stress/dfg-boolean-to-number-known-boolean-use-via-iterator-fast-path.js
    M Source/JavaScriptCore/CMakeLists.txt
    M Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj
    M Source/JavaScriptCore/Sources.txt
    M Source/JavaScriptCore/bytecode/IterationModeMetadata.h
    M Source/JavaScriptCore/dfg/DFGByteCodeParser.cpp
    M Source/JavaScriptCore/dfg/DFGSpeculativeJIT32_64.cpp
    M Source/JavaScriptCore/dfg/DFGSpeculativeJIT64.cpp
    M Source/JavaScriptCore/ftl/FTLLowerDFGToB3.cpp
    M Source/JavaScriptCore/heap/Heap.cpp
    M Source/JavaScriptCore/heap/Heap.h
    M Source/JavaScriptCore/jit/JIT.h
    M Source/JavaScriptCore/jit/JITCall.cpp
    M Source/JavaScriptCore/jit/JITInlines.h
    M Source/JavaScriptCore/jit/JITOperations.cpp
    M Source/JavaScriptCore/llint/LowLevelInterpreter32_64.asm
    M Source/JavaScriptCore/llint/LowLevelInterpreter64.asm
    M Source/JavaScriptCore/runtime/CommonSlowPaths.cpp
    M Source/JavaScriptCore/runtime/IteratorOperations.cpp
    M Source/JavaScriptCore/runtime/JSGlobalObject.cpp
    M Source/JavaScriptCore/runtime/JSGlobalObject.h
    M Source/JavaScriptCore/runtime/JSIteratorPrototype.cpp
    M Source/JavaScriptCore/runtime/JSIteratorPrototype.h
    A Source/JavaScriptCore/runtime/JSSentinel.cpp
    A Source/JavaScriptCore/runtime/JSSentinel.h
    A Source/JavaScriptCore/runtime/JSSentinelInlines.h
    M Source/JavaScriptCore/runtime/JSType.cpp
    M Source/JavaScriptCore/runtime/JSType.h
    M Source/JavaScriptCore/runtime/VM.cpp
    M Source/JavaScriptCore/runtime/VM.h

  Log Message:
  -----------
  [JSC] Add foundation of handling builtin iterators in fast-iteration-protocol
https://bugs.webkit.org/show_bug.cgi?id=315933
rdar://178341309

Reviewed by Sosuke Suzuki.

This patch introduces JSSentinel which carries opened iterator's
information from iterator_open to iterator_next. Previously we were
using empty value when fast-iterator-protocol started in iterator_open.
Instead, we start using JSSentinel. This can additionally carry
information about what kind of iterator is opened in
fast-iterator-protocol.

This is important since we can quickly offer which kind of iterator is
opened, like, array.values(), array.keys(), array.entries(). We can
offer this kind information as sentinel, and iterator_next will check
this to switch the implementation in DFG. By doing so, DFG does not need
to spread entire code of ArrayIterator#next, instead we can spread only
related kind's code.

By using this, we start supporting ArrayIterator with normal JSArray.
Now we added FastArrayValues, FastArrayKeys, and FastArrayEntries. And
DFG successfully emits corresponding code to them. FastArray mode gets
converted to FastArrayValues in iterator_next by sending FastArrayValues
sentinel value from iterator_open.

We do not remove JS builtin ArrayIterator#next yet as it is still
necessary for TypedArray's iteration: TypedArray unfortunately shares
ArrayIterator with JSArray. But we can next add FastTypedArrayXXX
to fast-iterator-protocol, and then we can support all possible
ArrayIterator use cases completely in DFG. This allows removing
ArrayIterator#next in JS and move it to C++ completely. This patch is
the first step towards that direction.

Also we can implement JSMap / JSSet iterations with different kinds as
well in this approach. And we can remove MapIterator#next and
SetIterator#next implementation in builtin JS next as well.

                                            ToT                     Patched

    array-iterator-fast-values        54.8006+-0.2046     ^     48.1993+-0.2089 
       ^ definitely 1.1370x faster
    array-iterator-fast-entries       96.0060+-1.6131     ^     70.2463+-0.2449 
       ^ definitely 1.3667x faster
    array-iterator-fast-keys          29.8394+-0.0329     ^     23.1626+-0.0437 
       ^ definitely 1.2883x faster

Tests: JSTests/microbenchmarks/array-iterator-fast-entries.js
       JSTests/microbenchmarks/array-iterator-fast-keys.js
       JSTests/microbenchmarks/array-iterator-fast-values.js
       JSTests/stress/array-iterator-fast-keys-values-entries.js

* JSTests/microbenchmarks/array-iterator-fast-entries.js: Added.
(arrayEntriesSum):
* JSTests/microbenchmarks/array-iterator-fast-keys.js: Added.
(arrayKeysSum):
* JSTests/microbenchmarks/array-iterator-fast-values.js: Added.
(arrayValues):
(arrayKeys):
(arrayEntries):
* JSTests/stress/array-iterator-fast-cross-realm.js: Added.
(shouldBe):
(valuesOfIterator):
(keysOfIterator):
(entriesOfIterator):
(consumeOneAndIterateRest):
(otherRealm.Array.prototype.Symbol.iterator):
(plainFor):
* JSTests/stress/array-iterator-fast-ftl.js: Added.
(shouldBe):
(values):
(keys):
(entries):
* 
JSTests/stress/array-iterator-fast-iterator-proto-symbol-iterator-overridden.js:
 Added.
(shouldBe):
(valuesOfIterator):
(iteratorPrototype.Symbol.iterator):
* JSTests/stress/array-iterator-fast-keys-values-entries.js: Added.
(shouldBe):
(values):
(keys):
(entries):
(mixed):
(valuesAfterReplacingValues):
(Array.prototype.values):
(valuesOfIterator):
* JSTests/stress/array-iterator-fast-mid-iteration.js: Added.
(shouldBe):
(consumeOneAndIterateRest):
(consumeKeysRest):
(consumeEntriesRest):
(drainThenIterate):
* JSTests/stress/array-iterator-fast-non-array-iterated-object.js: Added.
(shouldBe):
(sumValues):
(sumKeys):
(sumEntries):
(values):
(consumeOneAndIterateRest):
(iterateOrThrow):
* JSTests/stress/array-iterator-fast-own-symbol-iterator-on-instance.js: Added.
(shouldBe):
(sumIterator):
(customIter.Symbol.iterator):
* JSTests/stress/array-iterator-fast-watchpoint-invalidate-next.js: Added.
(shouldBe):
(values):
(plain):
(arrayIteratorPrototype.next):
* JSTests/stress/array-iterator-fast-watchpoint-invalidate-symbol-iterator.js: 
Added.
(shouldBe):
(values):
(plain):
(Array.prototype.Symbol.iterator):
* 
JSTests/stress/dfg-boolean-to-number-known-boolean-use-via-iterator-fast-path.js:
 Added.
(shouldBe):
(sumValuesIterator):
(sumKeysIterator):
(sumEntriesIterator):
(customValues.Symbol.iterator):
(customKeys.Symbol.iterator):
(customEntries.Symbol.iterator):
* Source/JavaScriptCore/CMakeLists.txt:
* Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj:
* Source/JavaScriptCore/Sources.txt:
* Source/JavaScriptCore/bytecode/IterationModeMetadata.h:
* Source/JavaScriptCore/dfg/DFGByteCodeParser.cpp:
(JSC::DFG::ByteCodeParser::handleIteratorOpen):
(JSC::DFG::ByteCodeParser::handleIteratorNext):
* Source/JavaScriptCore/dfg/DFGSpeculativeJIT32_64.cpp:
(JSC::DFG::SpeculativeJIT::compile):
* Source/JavaScriptCore/dfg/DFGSpeculativeJIT64.cpp:
(JSC::DFG::SpeculativeJIT::compile):
* Source/JavaScriptCore/ftl/FTLLowerDFGToB3.cpp:
(JSC::FTL::DFG::LowerDFGToB3::compileBooleanToNumber):
* Source/JavaScriptCore/heap/Heap.cpp:
* Source/JavaScriptCore/heap/Heap.h:
* Source/JavaScriptCore/jit/JIT.h:
* Source/JavaScriptCore/jit/JITCall.cpp:
(JSC::JIT::emit_op_iterator_next):
* Source/JavaScriptCore/jit/JITInlines.h:
(JSC::JIT::load16FromMetadata):
(JSC::JIT::store16ToMetadata):
* Source/JavaScriptCore/jit/JITOperations.cpp:
(JSC::JSC_DEFINE_JIT_OPERATION):
* Source/JavaScriptCore/llint/LowLevelInterpreter32_64.asm:
* Source/JavaScriptCore/llint/LowLevelInterpreter64.asm:
* Source/JavaScriptCore/runtime/CommonSlowPaths.cpp:
(JSC::iteratorOpenTryFastImpl):
(JSC::iteratorNextTryFastImpl):
* Source/JavaScriptCore/runtime/IteratorOperations.cpp:
(JSC::getIterationMode):
* Source/JavaScriptCore/runtime/JSGlobalObject.cpp:
(JSC::JSGlobalObject::init):
(JSC::JSGlobalObject::visitChildrenImpl):
* Source/JavaScriptCore/runtime/JSGlobalObject.h:
* Source/JavaScriptCore/runtime/JSIteratorPrototype.cpp:
(JSC::JSIteratorPrototype::finishCreation):
* Source/JavaScriptCore/runtime/JSIteratorPrototype.h:
* Source/JavaScriptCore/runtime/JSSentinel.cpp: Copied from 
Source/JavaScriptCore/bytecode/IterationModeMetadata.h.
* Source/JavaScriptCore/runtime/JSSentinel.h: Copied from 
Source/JavaScriptCore/bytecode/IterationModeMetadata.h.
* Source/JavaScriptCore/runtime/JSSentinelInlines.h: Copied from 
Source/JavaScriptCore/bytecode/IterationModeMetadata.h.
(JSC::JSSentinel::createStructure):
* Source/JavaScriptCore/runtime/JSType.cpp:
(WTF::printInternal):
* Source/JavaScriptCore/runtime/JSType.h:
* Source/JavaScriptCore/runtime/VM.cpp:
(JSC::VM::VM):
(JSC::VM::visitAggregateImpl):
* Source/JavaScriptCore/runtime/VM.h:
(JSC::VM::sentinelStructure):
(JSC::VM::fastArrayValuesSentinel):
(JSC::VM::fastArrayKeysSentinel):
(JSC::VM::fastArrayEntriesSentinel):
(JSC::VM::fastMapEntriesSentinel):
(JSC::VM::fastSetValuesSentinel):

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



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

Reply via email to