⚠ Archived content — this site is no longer maintained.   Current WebKit documentation is at docs.webkit.org.

Changeset 293152 in webkit


Ignore:
Timestamp:
Apr 21, 2022, 2:51:10 AM (4 years ago)
Author:
Carlos Garcia Campos
Message:

Merge r290788 - Add a DeferTraps scope
https://bugs.webkit.org/show_bug.cgi?id=237306
<rdar://83494949>

Reviewed by Mark Lam.

  • bytecode/CodeBlock.cpp:

(JSC::CodeBlock::CodeBlock):
(JSC::CodeBlock::jettison):
(JSC::CodeBlock::noticeIncomingCall):

  • bytecode/CodeBlock.h:
  • bytecode/RepatchInlines.h:

(JSC::linkFor):
(JSC::virtualForWithFunction):

  • dfg/DFGOperations.cpp:

(JSC::DFG::JSC_DEFINE_JIT_OPERATION):

  • interpreter/Interpreter.cpp:

(JSC::Interpreter::executeProgram):
(JSC::Interpreter::executeCall):
(JSC::Interpreter::executeConstruct):
(JSC::Interpreter::execute):
(JSC::Interpreter::executeModuleProgram):

  • interpreter/InterpreterInlines.h:

(JSC::Interpreter::execute):

  • llint/LLIntSlowPaths.cpp:

(JSC::LLInt::setUpCall):

  • runtime/ExceptionScope.h:
  • runtime/ScriptExecutable.cpp:

(JSC::ScriptExecutable::installCode):

  • runtime/VMTraps.cpp:

(JSC::VMTraps::handleTraps):
(JSC::VMTraps::takeTopPriorityTrap):

  • runtime/VMTraps.h:

(JSC::VMTraps::needHandling const):
(JSC::VMTraps::maybeNeedHandling const):
(JSC::VMTraps::hasTrapBit):
(JSC::VMTraps::setTrapBit):

  • runtime/VMTrapsInlines.h:

(JSC::DeferTraps::DeferTraps):
(JSC::DeferTraps::~DeferTraps):

Location:
releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore
Files:
13 edited

Legend:

Unmodified
Added
Removed
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/ChangeLog

    r291276 r293152  
     12022-03-03  Saam Barati  <sbarati@apple.com>
     2
     3        Add a DeferTraps scope
     4        https://bugs.webkit.org/show_bug.cgi?id=237306
     5        <rdar://83494949>
     6
     7        Reviewed by Mark Lam.
     8
     9        * bytecode/CodeBlock.cpp:
     10        (JSC::CodeBlock::CodeBlock):
     11        (JSC::CodeBlock::jettison):
     12        (JSC::CodeBlock::noticeIncomingCall):
     13        * bytecode/CodeBlock.h:
     14        * bytecode/RepatchInlines.h:
     15        (JSC::linkFor):
     16        (JSC::virtualForWithFunction):
     17        * dfg/DFGOperations.cpp:
     18        (JSC::DFG::JSC_DEFINE_JIT_OPERATION):
     19        * interpreter/Interpreter.cpp:
     20        (JSC::Interpreter::executeProgram):
     21        (JSC::Interpreter::executeCall):
     22        (JSC::Interpreter::executeConstruct):
     23        (JSC::Interpreter::execute):
     24        (JSC::Interpreter::executeModuleProgram):
     25        * interpreter/InterpreterInlines.h:
     26        (JSC::Interpreter::execute):
     27        * llint/LLIntSlowPaths.cpp:
     28        (JSC::LLInt::setUpCall):
     29        * runtime/ExceptionScope.h:
     30        * runtime/ScriptExecutable.cpp:
     31        (JSC::ScriptExecutable::installCode):
     32        * runtime/VMTraps.cpp:
     33        (JSC::VMTraps::handleTraps):
     34        (JSC::VMTraps::takeTopPriorityTrap):
     35        * runtime/VMTraps.h:
     36        (JSC::VMTraps::needHandling const):
     37        (JSC::VMTraps::maybeNeedHandling const):
     38        (JSC::VMTraps::hasTrapBit):
     39        (JSC::VMTraps::setTrapBit):
     40        * runtime/VMTrapsInlines.h:
     41        (JSC::DeferTraps::DeferTraps):
     42        (JSC::DeferTraps::~DeferTraps):
     43
    1442022-03-01  Michael Catanzaro  <mcatanzaro@gnome.org>
    245
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/bytecode/CodeBlock.cpp

    r290129 r293152  
    280280    , m_didFailFTLCompilation(false)
    281281    , m_hasBeenCompiledWithFTL(false)
     282    , m_isJettisoned(false)
    282283    , m_numCalleeLocals(other.m_numCalleeLocals)
    283284    , m_numVars(other.m_numVars)
     
    331332    , m_didFailFTLCompilation(false)
    332333    , m_hasBeenCompiledWithFTL(false)
     334    , m_isJettisoned(false)
    333335    , m_numCalleeLocals(unlinkedCodeBlock->numCalleeLocals())
    334336    , m_numVars(unlinkedCodeBlock->numVars())
     
    21912193    VM& vm = *m_vm;
    21922194
     2195    m_isJettisoned = true;
     2196
    21932197    CodeBlock* codeBlock = this; // Placate GCC for use in CODEBLOCK_LOG_EVENT  (does not like this).
    21942198    CODEBLOCK_LOG_EVENT(codeBlock, "jettison", ("due to ", reason, ", counting = ", mode == CountReoptimization, ", detail = ", pointerDump(detail)));
     
    23572361void CodeBlock::noticeIncomingCall(CallFrame* callerFrame)
    23582362{
     2363    RELEASE_ASSERT(!m_isJettisoned);
     2364
    23592365    CodeBlock* callerCodeBlock = callerFrame->codeBlock();
    23602366   
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/bytecode/CodeBlock.h

    r287596 r293152  
    775775    bool m_didFailFTLCompilation : 1;
    776776    bool m_hasBeenCompiledWithFTL : 1;
     777    bool m_isJettisoned : 1;
    777778
    778779    bool m_visitChildrenSkippedDueToOldAge { false };
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/bytecode/RepatchInlines.h

    r286095 r293152  
    2828#include "Repatch.h"
    2929
     30#include "VMTrapsInlines.h"
     31
    3032namespace JSC {
    3133
     
    125127    MacroAssemblerCodePtr<JSEntryPtrTag> codePtr;
    126128    CodeBlock* codeBlock = nullptr;
     129
     130    DeferTraps deferTraps(vm); // We can't jettison any code until after we link the call.
     131
    127132    if (executable->isHostFunction()) {
    128133        codePtr = jsToWasmICCodePtr(vm, kind, callee);
     
    188193    JSScope* scope = function->scopeUnchecked();
    189194    ExecutableBase* executable = function->executable();
     195
     196    DeferTraps deferTraps(vm); // We can't jettison if we're going to call this CodeBlock.
     197
    190198    if (UNLIKELY(!executable->hasJITCodeFor(kind))) {
    191199        FunctionExecutable* functionExecutable = static_cast<FunctionExecutable*>(executable);
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/dfg/DFGOperations.cpp

    r286769 r293152  
    7979#include "TypeProfilerLog.h"
    8080#include "VMInlines.h"
     81#include "VMTrapsInlines.h"
    8182
    8283#if ENABLE(JIT)
     
    37133714    MacroAssemblerCodePtr<JSEntryPtrTag> codePtr;
    37143715    CodeBlock* codeBlock = nullptr;
     3716    DeferTraps deferTraps(vm); // We can't jettison this code if we're about to link to it.
     3717
    37153718    if (executable->isHostFunction())
    37163719        codePtr = executable->entrypointFor(kind, MustCheckArity);
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/interpreter/Interpreter.cpp

    r290283 r293152  
    924924        scope->flattenDictionaryObject(vm);
    925925
    926     ProgramCodeBlock* codeBlock;
    927     {
    928         CodeBlock* tempCodeBlock;
    929         program->prepareForExecution<ProgramExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
    930         RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
    931 
    932         codeBlock = jsCast<ProgramCodeBlock*>(tempCodeBlock);
    933         ASSERT(codeBlock && codeBlock->numParameters() == 1); // 1 parameter for 'this'.
    934     }
    935 
    936926    RefPtr<JITCode> jitCode;
    937927    ProtoCallFrame protoCallFrame;
    938928    {
    939         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    940         jitCode = program->generatedJITCode();
    941         protoCallFrame.init(codeBlock, globalObject, globalCallee, thisObj, 1);
     929        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     930
     931        ProgramCodeBlock* codeBlock;
     932        {
     933            CodeBlock* tempCodeBlock;
     934            program->prepareForExecution<ProgramExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
     935            RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     936
     937            codeBlock = jsCast<ProgramCodeBlock*>(tempCodeBlock);
     938            ASSERT(codeBlock && codeBlock->numParameters() == 1); // 1 parameter for 'this'.
     939        }
     940
     941        {
     942            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     943            jitCode = program->generatedJITCode();
     944            protoCallFrame.init(codeBlock, globalObject, globalCallee, thisObj, 1);
     945        }
    942946    }
    943947
     
    986990    }
    987991
    988     CodeBlock* newCodeBlock = nullptr;
    989     if (isJSCall) {
    990         // Compile the callee:
    991         callData.js.functionExecutable->prepareForExecution<FunctionExecutable>(vm, jsCast<JSFunction*>(function), scope, CodeForCall, newCodeBlock);
    992         RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
    993 
    994         ASSERT(newCodeBlock);
    995         newCodeBlock->m_shouldAlwaysBeInlined = false;
    996     }
    997 
    998992    RefPtr<JITCode> jitCode;
    999993    ProtoCallFrame protoCallFrame;
    1000994    {
    1001         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    1002         if (isJSCall)
    1003             jitCode = callData.js.functionExecutable->generatedJITCodeForCall();
    1004         protoCallFrame.init(newCodeBlock, globalObject, function, thisValue, argsCount, args.data());
     995        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     996
     997        CodeBlock* newCodeBlock = nullptr;
     998        if (isJSCall) {
     999            // Compile the callee:
     1000            callData.js.functionExecutable->prepareForExecution<FunctionExecutable>(vm, jsCast<JSFunction*>(function), scope, CodeForCall, newCodeBlock);
     1001            RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     1002
     1003            ASSERT(newCodeBlock);
     1004            newCodeBlock->m_shouldAlwaysBeInlined = false;
     1005        }
     1006
     1007        {
     1008            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     1009            if (isJSCall)
     1010                jitCode = callData.js.functionExecutable->generatedJITCodeForCall();
     1011            protoCallFrame.init(newCodeBlock, globalObject, function, thisValue, argsCount, args.data());
     1012        }
    10051013    }
    10061014
     
    10621070    }
    10631071
    1064     CodeBlock* newCodeBlock = nullptr;
    1065     if (isJSConstruct) {
    1066         // Compile the callee:
    1067         constructData.js.functionExecutable->prepareForExecution<FunctionExecutable>(vm, jsCast<JSFunction*>(constructor), scope, CodeForConstruct, newCodeBlock);
    1068         RETURN_IF_EXCEPTION(throwScope, nullptr);
    1069 
    1070         ASSERT(newCodeBlock);
    1071         newCodeBlock->m_shouldAlwaysBeInlined = false;
    1072     }
    1073 
    10741072    RefPtr<JITCode> jitCode;
    10751073    ProtoCallFrame protoCallFrame;
    10761074    {
    1077         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    1078         if (isJSConstruct)
    1079             jitCode = constructData.js.functionExecutable->generatedJITCodeForConstruct();
    1080         protoCallFrame.init(newCodeBlock, globalObject, constructor, newTarget, argsCount, args.data());
     1075        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     1076
     1077        CodeBlock* newCodeBlock = nullptr;
     1078        if (isJSConstruct) {
     1079            // Compile the callee:
     1080            constructData.js.functionExecutable->prepareForExecution<FunctionExecutable>(vm, jsCast<JSFunction*>(constructor), scope, CodeForConstruct, newCodeBlock);
     1081            RETURN_IF_EXCEPTION(throwScope, nullptr);
     1082
     1083            ASSERT(newCodeBlock);
     1084            newCodeBlock->m_shouldAlwaysBeInlined = false;
     1085        }
     1086
     1087        {
     1088            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     1089            if (isJSConstruct)
     1090                jitCode = constructData.js.functionExecutable->generatedJITCodeForConstruct();
     1091            protoCallFrame.init(newCodeBlock, globalObject, constructor, newTarget, argsCount, args.data());
     1092        }
    10811093    }
    10821094
     
    12701282        callee = JSCallee::create(vm, globalObject, scope);
    12711283
    1272     // Reload CodeBlock. It is possible that we replaced CodeBlock while setting up the environment.
    1273     {
    1274         CodeBlock* tempCodeBlock;
    1275         eval->prepareForExecution<EvalExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
    1276         RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
    1277 
    1278         codeBlock = jsCast<EvalCodeBlock*>(tempCodeBlock);
    1279         ASSERT(codeBlock && codeBlock->numParameters() == 1); // 1 parameter for 'this'.
    1280     }
    1281 
    12821284    RefPtr<JITCode> jitCode;
    12831285    ProtoCallFrame protoCallFrame;
    12841286    {
    1285         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    1286         jitCode = eval->generatedJITCode();
    1287         protoCallFrame.init(codeBlock, globalObject, callee, thisValue, 1);
     1287        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     1288
     1289        // Reload CodeBlock. It is possible that we replaced CodeBlock while setting up the environment.
     1290        {
     1291            CodeBlock* tempCodeBlock;
     1292            eval->prepareForExecution<EvalExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
     1293            RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     1294
     1295            codeBlock = jsCast<EvalCodeBlock*>(tempCodeBlock);
     1296            ASSERT(codeBlock && codeBlock->numParameters() == 1); // 1 parameter for 'this'.
     1297        }
     1298
     1299        {
     1300            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     1301            jitCode = eval->generatedJITCode();
     1302            protoCallFrame.init(codeBlock, globalObject, callee, thisValue, 1);
     1303        }
    12881304    }
    12891305
     
    13271343    const unsigned numberOfArguments = static_cast<unsigned>(AbstractModuleRecord::Argument::NumberOfArguments);
    13281344    JSCallee* callee = JSCallee::create(vm, globalObject, scope);
    1329     ModuleProgramCodeBlock* codeBlock;
    1330     {
    1331         CodeBlock* tempCodeBlock;
    1332         executable->prepareForExecution<ModuleProgramExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
    1333         RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
    1334 
    1335         codeBlock = jsCast<ModuleProgramCodeBlock*>(tempCodeBlock);
    1336         ASSERT(codeBlock && codeBlock->numParameters() == numberOfArguments + 1);
    1337     }
    1338 
    13391345    RefPtr<JITCode> jitCode;
     1346
    13401347    ProtoCallFrame protoCallFrame;
    13411348    JSValue args[numberOfArguments] = {
     
    13481355
    13491356    {
    1350         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    1351         jitCode = executable->generatedJITCode();
    1352 
    1353         // The |this| of the module is always `undefined`.
    1354         // http://www.ecma-international.org/ecma-262/6.0/#sec-module-environment-records-hasthisbinding
    1355         // http://www.ecma-international.org/ecma-262/6.0/#sec-module-environment-records-getthisbinding
    1356         protoCallFrame.init(codeBlock, globalObject, callee, jsUndefined(), numberOfArguments + 1, args);
    1357     }
    1358 
    1359     record->internalField(JSModuleRecord::Field::State).set(vm, record, jsNumber(static_cast<int>(JSModuleRecord::State::Executing)));
     1357        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     1358
     1359        ModuleProgramCodeBlock* codeBlock;
     1360        {
     1361            CodeBlock* tempCodeBlock;
     1362            executable->prepareForExecution<ModuleProgramExecutable>(vm, nullptr, scope, CodeForCall, tempCodeBlock);
     1363            RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     1364
     1365            codeBlock = jsCast<ModuleProgramCodeBlock*>(tempCodeBlock);
     1366            ASSERT(codeBlock && codeBlock->numParameters() == numberOfArguments + 1);
     1367        }
     1368
     1369
     1370        {
     1371            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     1372            jitCode = executable->generatedJITCode();
     1373
     1374            // The |this| of the module is always `undefined`.
     1375            // http://www.ecma-international.org/ecma-262/6.0/#sec-module-environment-records-hasthisbinding
     1376            // http://www.ecma-international.org/ecma-262/6.0/#sec-module-environment-records-getthisbinding
     1377            protoCallFrame.init(codeBlock, globalObject, callee, jsUndefined(), numberOfArguments + 1, args);
     1378        }
     1379
     1380        record->internalField(JSModuleRecord::Field::State).set(vm, record, jsNumber(static_cast<int>(JSModuleRecord::State::Executing)));
     1381    }
    13601382
    13611383    // Execute the code:
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/interpreter/InterpreterInlines.h

    r281939 r293152  
    3737#include "ProtoCallFrameInlines.h"
    3838#include "UnlinkedCodeBlock.h"
     39#include "VMTrapsInlines.h"
    3940#include <wtf/UnalignedAccess.h>
    4041
     
    8788    }
    8889
    89     // Reload CodeBlock since GC can replace CodeBlock owned by Executable.
    90     CodeBlock* codeBlock;
    91     closure.functionExecutable->prepareForExecution<FunctionExecutable>(vm, closure.function, closure.scope, CodeForCall, codeBlock);
    92     RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     90    {
     91        DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
    9392
    94     ASSERT(codeBlock);
    95     codeBlock->m_shouldAlwaysBeInlined = false;
    96     {
    97         DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
    98         closure.protoCallFrame->setCodeBlock(codeBlock);
     93        // Reload CodeBlock since GC can replace CodeBlock owned by Executable.
     94        CodeBlock* codeBlock;
     95        closure.functionExecutable->prepareForExecution<FunctionExecutable>(vm, closure.function, closure.scope, CodeForCall, codeBlock);
     96        RETURN_IF_EXCEPTION(throwScope, checkedReturn(throwScope.exception()));
     97
     98        ASSERT(codeBlock);
     99        codeBlock->m_shouldAlwaysBeInlined = false;
     100        {
     101            DisallowGC disallowGC; // Ensure no GC happens. GC can replace CodeBlock in Executable.
     102            closure.protoCallFrame->setCodeBlock(codeBlock);
     103        }
    99104    }
     105
    100106    // Execute the code:
    101107    throwScope.release();
    102108    JSValue result = closure.functionExecutable->generatedJITCodeForCall()->execute(&vm, closure.protoCallFrame);
    103 
    104109    return checkedReturn(result);
    105110}
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/llint/LLIntSlowPaths.cpp

    r288815 r293152  
    6767#include "SuperSampler.h"
    6868#include "VMInlines.h"
     69#include "VMTrapsInlines.h"
    6970#include <wtf/NeverDestroyed.h>
    7071#include <wtf/StringPrintStream.h>
     
    19051906    ExecutableBase* executable = callee->executable();
    19061907
     1908    DeferTraps deferTraps(vm); // We can't jettison this code if we're about to run it.
     1909
    19071910    MacroAssemblerCodePtr<JSEntryPtrTag> codePtr;
    1908     CodeBlock* codeBlock = nullptr;
    19091911    // FIXME: Support wasm IC.
    19101912    // https://bugs.webkit.org/show_bug.cgi?id=220339
     
    19201922        LLINT_CALL_CHECK_EXCEPTION(globalObject);
    19211923
    1922         codeBlock = *codeBlockSlot;
     1924        CodeBlock* codeBlock = *codeBlockSlot;
    19231925        ASSERT(codeBlock);
    19241926
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/runtime/ExceptionScope.h

    r277068 r293152  
    111111        JSC::VM& vm = (scope__).vm(); \
    112112        ASSERT(!!(scope__).exception() == vm.traps().needHandling(JSC::VMTraps::NeedExceptionHandling)); \
    113         if (UNLIKELY(vm.traps().needHandling(JSC::VMTraps::NonDebuggerEvents))) { \
     113        if (UNLIKELY(vm.traps().maybeNeedHandling(JSC::VMTraps::NonDebuggerEvents))) { \
    114114            if (vm.hasExceptionsAfterHandlingTraps()) \
    115115                return value__; \
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/runtime/ScriptExecutable.cpp

    r290129 r293152  
    197197        RELEASE_ASSERT(genericCodeBlock->ownerExecutable() == this);
    198198        RELEASE_ASSERT(JITCode::isExecutableScript(genericCodeBlock->jitType()));
     199
     200        genericCodeBlock->m_isJettisoned = false;
    199201       
    200202        dataLogLnIf(Options::verboseOSR(), "Installing ", *genericCodeBlock);
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/runtime/VMTraps.cpp

    r289159 r293152  
    350350    ASSERT(onlyContainsAsyncEvents(mask));
    351351    ASSERT(needHandling(mask));
     352    ASSERT(!hasTrapBit(DeferTrapHandling));
    352353
    353354    if (isDeferringTermination())
     
    391392
    392393        case NeedExceptionHandling:
     394        case DeferTrapHandling:
    393395        default:
    394396            RELEASE_ASSERT_NOT_REACHED();
     
    403405    // Note: the EventBitShift is already sorted in highest to lowest priority
    404406    // i.e. a bit shift of 0 is highest priority, etc.
    405     for (int i = 0; i < NumberOfEvents; ++i) {
     407    for (unsigned i = 0; i < NumberOfEvents; ++i) {
    406408        Event event = static_cast<Event>(1 << i);
    407409        if (hasTrapBit(event, mask)) {
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/runtime/VMTraps.h

    r280761 r293152  
    150150    v(NeedWatchdogCheck) \
    151151    v(NeedDebuggerBreak) \
    152     v(NeedExceptionHandling)
     152    v(NeedExceptionHandling) \
     153    v(DeferTrapHandling) // Must come last in the enum. This defers all events except NeedExceptionHandling.
    153154
    154155#define DECLARE_VMTRAPS_EVENT_BIT_SHIFT(event__)  event__##BitShift,
    155156    enum EventBitShift {
    156157        FOR_EACH_VMTRAPS_EVENTS(DECLARE_VMTRAPS_EVENT_BIT_SHIFT)
    157         NumberOfEvents, // This entry must be last in this list.
    158158    };
    159159#undef DECLARE_VMTRAPS_EVENT_BIT_SHIFT
     160
     161
     162#define COUNT_EVENT(event) + 1
     163    static constexpr BitField NumberOfEvents = FOR_EACH_VMTRAPS_EVENTS(COUNT_EVENT) - 1; // Don't count DeferTrapHandling.
     164    static constexpr BitField NumberOfEventsIncludingDefer = FOR_EACH_VMTRAPS_EVENTS(COUNT_EVENT);
     165#undef COUNT_EVENT
    160166
    161167    using Event = BitField;
     
    171177    static constexpr Event NoEvent = 0;
    172178
    173     static_assert(NumberOfEvents <= bitsInBitField);
     179    static_assert(NumberOfEventsIncludingDefer <= bitsInBitField);
    174180    static constexpr BitField AllEvents = (1ull << NumberOfEvents) - 1;
     181    static constexpr BitField AllEventsIncludingDefer = (1ull << NumberOfEventsIncludingDefer) - 1;
    175182    static constexpr BitField AsyncEvents = AllEvents & ~NeedExceptionHandling;
    176183    static constexpr BitField NonDebuggerEvents = AllEvents & ~NeedDebuggerBreak;
     
    189196    void willDestroyVM();
    190197
    191     bool needHandling(BitField mask) const { return m_trapBits.loadRelaxed() & mask; }
     198    ALWAYS_INLINE bool needHandling(BitField mask) const
     199    {
     200        auto maskedValue = m_trapBits.loadRelaxed() & (mask | DeferTrapHandling);
     201        if (UNLIKELY(maskedValue))
     202            return (maskedValue & NeedExceptionHandling) || !(maskedValue & DeferTrapHandling);
     203        return false;
     204    }
     205    // Designed to be a fast check to rule out if we might need handling, and we need to ensure needHandling on the slow path.
     206    ALWAYS_INLINE bool maybeNeedHandling(BitField mask) const { return m_trapBits.loadRelaxed() & mask; }
    192207    void* trapBitsAddress() { return &m_trapBits; }
    193208
     
    207222    }
    208223
     224    bool hasTrapBit(Event event)
     225    {
     226        return m_trapBits.loadRelaxed() & event;
     227    }
    209228    bool hasTrapBit(Event event, BitField mask)
    210229    {
     
    215234    void setTrapBit(Event event)
    216235    {
    217         ASSERT((event & ~AllEvents) == 0);
     236        ASSERT((event & ~AllEventsIncludingDefer) == 0);
    218237        m_trapBits.exchangeOr(event);
    219238    }
     
    267286};
    268287
     288class DeferTraps {
     289public:
     290    DeferTraps(VM&);
     291    ~DeferTraps();
     292private:
     293    VMTraps& m_traps;
     294    bool m_isActive;
     295};
     296
    269297} // namespace JSC
  • releases/WebKitGTK/webkit-2.36/Source/JavaScriptCore/runtime/VMTrapsInlines.h

    r276069 r293152  
    5151}
    5252
     53ALWAYS_INLINE DeferTraps::DeferTraps(VM& vm)
     54    : m_traps(vm.traps())
     55    , m_isActive(!m_traps.hasTrapBit(VMTraps::DeferTrapHandling))
     56{
     57    if (m_isActive)
     58        m_traps.setTrapBit(VMTraps::DeferTrapHandling);
     59}
     60
     61ALWAYS_INLINE DeferTraps::~DeferTraps()
     62{
     63    if (m_isActive)
     64        m_traps.clearTrapBit(VMTraps::DeferTrapHandling);
     65}
     66
    5367} // namespace JSC
Note: See TracChangeset for help on using the changeset viewer.