Title: [295585] trunk/Source/_javascript_Core
Revision
295585
Author
sbar...@apple.com
Date
2022-06-15 22:31:25 -0700 (Wed, 15 Jun 2022)

Log Message

Don't clear both prototype ICs for LLInt iterator_next
https://bugs.webkit.org/show_bug.cgi?id=241663

Reviewed by Yusuke Suzuki.

If we use BytecodeIndex instead of a bytecode offset, we don't need to
clear both ICs. We can just clear the one that the watchpoint fired for.

* Source/_javascript_Core/bytecode/CodeBlock.cpp:
(JSC::CodeBlock::finalizeLLIntInlineCaches):
* Source/_javascript_Core/bytecode/CodeBlock.h:
* Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.cpp:
(JSC::LLIntPrototypeLoadAdaptiveStructureWatchpoint::LLIntPrototypeLoadAdaptiveStructureWatchpoint):
(JSC::LLIntPrototypeLoadAdaptiveStructureWatchpoint::initialize):
(JSC::LLIntPrototypeLoadAdaptiveStructureWatchpoint::fireInternal):
* Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.h:
* Source/_javascript_Core/llint/LLIntSlowPaths.cpp:
(JSC::LLInt::setupGetByIdPrototypeCache):
(JSC::LLInt::performLLIntGetByID):
(JSC::LLInt::LLINT_SLOW_PATH_DECL):

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

Modified Paths

Diff

Modified: trunk/Source/_javascript_Core/bytecode/CodeBlock.cpp (295584 => 295585)


--- trunk/Source/_javascript_Core/bytecode/CodeBlock.cpp	2022-06-16 04:57:11 UTC (rev 295584)
+++ trunk/Source/_javascript_Core/bytecode/CodeBlock.cpp	2022-06-16 05:31:25 UTC (rev 295585)
@@ -1547,7 +1547,8 @@
     // then cleared the cache without GCing in between.
     m_llintGetByIdWatchpointMap.removeIf([&] (const StructureWatchpointMap::KeyValuePairType& pair) -> bool {
         auto clear = [&] () {
-            auto& instruction = instructions().at(std::get<1>(pair.key));
+            BytecodeIndex bytecodeIndex = std::get<1>(pair.key);
+            auto& instruction = instructions().at(bytecodeIndex.offset());
             OpcodeID opcode = instruction->opcodeID();
             switch (opcode) {
             case op_get_by_id: {

Modified: trunk/Source/_javascript_Core/bytecode/CodeBlock.h (295584 => 295585)


--- trunk/Source/_javascript_Core/bytecode/CodeBlock.h	2022-06-16 04:57:11 UTC (rev 295584)
+++ trunk/Source/_javascript_Core/bytecode/CodeBlock.h	2022-06-16 05:31:25 UTC (rev 295585)
@@ -591,7 +591,7 @@
         return m_unlinkedCode->llintExecuteCounter();
     }
 
-    typedef HashMap<std::tuple<StructureID, unsigned>, FixedVector<LLIntPrototypeLoadAdaptiveStructureWatchpoint>> StructureWatchpointMap;
+    typedef HashMap<std::tuple<StructureID, BytecodeIndex>, FixedVector<LLIntPrototypeLoadAdaptiveStructureWatchpoint>> StructureWatchpointMap;
     StructureWatchpointMap& llintGetByIdWatchpointMap() { return m_llintGetByIdWatchpointMap; }
 
     // Functions for controlling when tiered compilation kicks in. This

Modified: trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.cpp (295584 => 295585)


--- trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.cpp	2022-06-16 04:57:11 UTC (rev 295584)
+++ trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.cpp	2022-06-16 05:31:25 UTC (rev 295585)
@@ -32,10 +32,10 @@
 
 namespace JSC {
 
-LLIntPrototypeLoadAdaptiveStructureWatchpoint::LLIntPrototypeLoadAdaptiveStructureWatchpoint(CodeBlock* owner, const ObjectPropertyCondition& key, unsigned bytecodeOffset)
+LLIntPrototypeLoadAdaptiveStructureWatchpoint::LLIntPrototypeLoadAdaptiveStructureWatchpoint(CodeBlock* owner, const ObjectPropertyCondition& key, BytecodeIndex bytecodeIndex)
     : Watchpoint(Watchpoint::Type::LLIntPrototypeLoadAdaptiveStructure)
     , m_owner(owner)
-    , m_bytecodeOffset(bytecodeOffset)
+    , m_bytecodeIndex(bytecodeIndex)
     , m_key(key)
 {
     RELEASE_ASSERT(key.watchingRequiresStructureTransitionWatchpoint());
@@ -45,14 +45,13 @@
 LLIntPrototypeLoadAdaptiveStructureWatchpoint::LLIntPrototypeLoadAdaptiveStructureWatchpoint()
     : Watchpoint(Watchpoint::Type::LLIntPrototypeLoadAdaptiveStructure)
     , m_owner(nullptr)
-    , m_bytecodeOffset(0)
 {
 }
 
-void LLIntPrototypeLoadAdaptiveStructureWatchpoint::initialize(CodeBlock* codeBlock, const ObjectPropertyCondition& key, unsigned bytecodeOffset)
+void LLIntPrototypeLoadAdaptiveStructureWatchpoint::initialize(CodeBlock* codeBlock, const ObjectPropertyCondition& key, BytecodeIndex bytecodeOffset)
 {
     m_owner = codeBlock;
-    m_bytecodeOffset = bytecodeOffset;
+    m_bytecodeIndex = bytecodeOffset;
     m_key = key;
 }
 
@@ -73,7 +72,7 @@
         return;
     }
 
-    auto& instruction = m_owner->instructions().at(m_bytecodeOffset.get());
+    auto& instruction = m_owner->instructions().at(m_bytecodeIndex.get().offset());
     switch (instruction->opcodeID()) {
     case op_get_by_id:
         clearLLIntGetByIdCache(instruction->as<OpGetById>().metadata(m_owner.get()).m_modeMetadata);
@@ -85,8 +84,16 @@
 
     case op_iterator_next: {
         auto& metadata = instruction->as<OpIteratorNext>().metadata(m_owner.get());
-        clearLLIntGetByIdCache(metadata.m_doneModeMetadata);
-        clearLLIntGetByIdCache(metadata.m_valueModeMetadata);
+        switch (m_bytecodeIndex.get().checkpoint()) {
+        case OpIteratorNext::getDone:
+            clearLLIntGetByIdCache(metadata.m_doneModeMetadata);
+            break;
+        case OpIteratorNext::getValue:
+            clearLLIntGetByIdCache(metadata.m_valueModeMetadata);
+            break;
+        default:
+            RELEASE_ASSERT_NOT_REACHED();
+        }
         break;
     }
 

Modified: trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.h (295584 => 295585)


--- trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.h	2022-06-16 04:57:11 UTC (rev 295584)
+++ trunk/Source/_javascript_Core/bytecode/LLIntPrototypeLoadAdaptiveStructureWatchpoint.h	2022-06-16 05:31:25 UTC (rev 295585)
@@ -35,10 +35,10 @@
 
 class LLIntPrototypeLoadAdaptiveStructureWatchpoint final : public Watchpoint {
 public:
-    LLIntPrototypeLoadAdaptiveStructureWatchpoint(CodeBlock*, const ObjectPropertyCondition&, unsigned bytecodeOffset);
+    LLIntPrototypeLoadAdaptiveStructureWatchpoint(CodeBlock*, const ObjectPropertyCondition&, BytecodeIndex);
     LLIntPrototypeLoadAdaptiveStructureWatchpoint();
 
-    void initialize(CodeBlock*, const ObjectPropertyCondition&, unsigned bytecodeOffset);
+    void initialize(CodeBlock*, const ObjectPropertyCondition&, BytecodeIndex);
 
     void install(VM&);
 
@@ -51,7 +51,7 @@
 private:
     // Own destructor may not be called. Keep members trivially destructible.
     JSC_WATCHPOINT_FIELD(PackedCellPtr<CodeBlock>, m_owner);
-    JSC_WATCHPOINT_FIELD(Packed<unsigned>, m_bytecodeOffset);
+    JSC_WATCHPOINT_FIELD(Packed<BytecodeIndex>, m_bytecodeIndex);
     JSC_WATCHPOINT_FIELD(ObjectPropertyCondition, m_key);
 };
 

Modified: trunk/Source/_javascript_Core/llint/LLIntSlowPaths.cpp (295584 => 295585)


--- trunk/Source/_javascript_Core/llint/LLIntSlowPaths.cpp	2022-06-16 04:57:11 UTC (rev 295584)
+++ trunk/Source/_javascript_Core/llint/LLIntSlowPaths.cpp	2022-06-16 05:31:25 UTC (rev 295585)
@@ -746,7 +746,7 @@
     LLINT_RETURN_PROFILED(result);
 }
 
-static void setupGetByIdPrototypeCache(JSGlobalObject* globalObject, VM& vm, CodeBlock* codeBlock, const JSInstruction* pc, GetByIdModeMetadata& metadata, JSCell* baseCell, PropertySlot& slot, const Identifier& ident)
+static void setupGetByIdPrototypeCache(JSGlobalObject* globalObject, VM& vm, CodeBlock* codeBlock, BytecodeIndex bytecodeIndex, GetByIdModeMetadata& metadata, JSCell* baseCell, PropertySlot& slot, const Identifier& ident)
 {
     Structure* structure = baseCell->structure();
 
@@ -773,7 +773,6 @@
     if (!conditions.isValid())
         return;
 
-    unsigned bytecodeOffset = codeBlock->bytecodeOffset(pc);
     PropertyOffset offset = invalidOffset;
     CodeBlock::StructureWatchpointMap& watchpointMap = codeBlock->llintGetByIdWatchpointMap();
     FixedVector<LLIntPrototypeLoadAdaptiveStructureWatchpoint> watchpoints(conditions.size());
@@ -784,12 +783,12 @@
             return;
         if (condition.condition().kind() == PropertyCondition::Presence)
             offset = condition.condition().offset();
-        watchpoint.initialize(codeBlock, condition, bytecodeOffset);
+        watchpoint.initialize(codeBlock, condition, bytecodeIndex);
         watchpoint.install(vm);
     }
 
     ASSERT((offset == invalidOffset) == slot.isUnset());
-    auto result = watchpointMap.add(std::make_tuple(structure->id(), bytecodeOffset), WTFMove(watchpoints));
+    auto result = watchpointMap.add(std::make_tuple(structure->id(), bytecodeIndex), WTFMove(watchpoints));
     ASSERT_UNUSED(result, result.isNewEntry);
 
     {
@@ -804,7 +803,7 @@
     vm.writeBarrier(codeBlock);
 }
 
-static JSValue performLLIntGetByID(const JSInstruction* pc, CodeBlock* codeBlock, JSGlobalObject* globalObject, JSValue baseValue, const Identifier& ident, GetByIdModeMetadata& metadata)
+static JSValue performLLIntGetByID(BytecodeIndex bytecodeIndex, CodeBlock* codeBlock, JSGlobalObject* globalObject, JSValue baseValue, const Identifier& ident, GetByIdModeMetadata& metadata)
 {
     VM& vm = globalObject->vm();
     auto throwScope = DECLARE_THROW_SCOPE(vm);
@@ -862,7 +861,7 @@
             ASSERT(slot.slotBase() != baseValue);
 
             if (!(--metadata.hitCountForLLIntCaching))
-                setupGetByIdPrototypeCache(globalObject, vm, codeBlock, pc, metadata, baseCell, slot, ident);
+                setupGetByIdPrototypeCache(globalObject, vm, codeBlock, bytecodeIndex, metadata, baseCell, slot, ident);
         }
     } else if (Options::useLLIntICs() && isJSArray(baseValue) && ident == vm.propertyNames->length) {
         {
@@ -884,7 +883,7 @@
     const Identifier& ident = codeBlock->identifier(bytecode.m_property);
     JSValue baseValue = getOperand(callFrame, bytecode.m_base);
 
-    JSValue result = performLLIntGetByID(pc, codeBlock, globalObject, baseValue, ident, metadata.m_modeMetadata);
+    JSValue result = performLLIntGetByID(codeBlock->bytecodeIndex(pc), codeBlock, globalObject, baseValue, ident, metadata.m_modeMetadata);
     LLINT_RETURN_PROFILED(result);
 }
 
@@ -900,7 +899,7 @@
     if (!iterator.isObject())
         LLINT_THROW(createTypeError(globalObject, "Iterator result interface is not an object."_s));
 
-    JSValue result = performLLIntGetByID(pc, codeBlock, globalObject, iterator, vm.propertyNames->next, metadata.m_modeMetadata);
+    JSValue result = performLLIntGetByID(codeBlock->bytecodeIndex(pc).withCheckpoint(OpIteratorOpen::getNext), codeBlock, globalObject, iterator, vm.propertyNames->next, metadata.m_modeMetadata);
     LLINT_CHECK_EXCEPTION();
     nextRegister = result;
     bytecode.metadata(codeBlock).m_nextProfile.m_buckets[0] = JSValue::encode(result);
@@ -920,7 +919,7 @@
     if (!iteratorReturn.isObject())
         LLINT_THROW(createTypeError(globalObject, "Iterator result interface is not an object."_s));
 
-    JSValue result = performLLIntGetByID(pc, codeBlock, globalObject, iteratorReturn, vm.propertyNames->done, metadata.m_doneModeMetadata);
+    JSValue result = performLLIntGetByID(codeBlock->bytecodeIndex(pc).withCheckpoint(OpIteratorNext::getDone), codeBlock, globalObject, iteratorReturn, vm.propertyNames->done, metadata.m_doneModeMetadata);
     LLINT_CHECK_EXCEPTION();
     doneRegister = result;
     bytecode.metadata(codeBlock).m_doneProfile.m_buckets[0] = JSValue::encode(result);
@@ -937,7 +936,7 @@
     Register& valueRegister = callFrame->uncheckedR(bytecode.m_value);
     JSValue iteratorReturn = valueRegister.jsValue();
 
-    JSValue result = performLLIntGetByID(pc, codeBlock, globalObject, iteratorReturn, vm.propertyNames->value, metadata.m_valueModeMetadata);
+    JSValue result = performLLIntGetByID(codeBlock->bytecodeIndex(pc).withCheckpoint(OpIteratorNext::getValue), codeBlock, globalObject, iteratorReturn, vm.propertyNames->value, metadata.m_valueModeMetadata);
     LLINT_CHECK_EXCEPTION();
     valueRegister = result;
     bytecode.metadata(codeBlock).m_valueProfile.m_buckets[0] = JSValue::encode(result);
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to