DFG and FTL should have an OSR exit fuzzer
authorfpizlo@apple.com <fpizlo@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 3 Jul 2015 01:48:01 +0000 (01:48 +0000)
committerfpizlo@apple.com <fpizlo@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 3 Jul 2015 01:48:01 +0000 (01:48 +0000)
https://bugs.webkit.org/show_bug.cgi?id=146562

Reviewed by Benjamin Poulain.

Adds a basic OSR exit fuzzer to JSC. This isn't hooked into any test harnesses yet, but I
spot-checked it on v8-earley-boyer.js and so far found no bugs. I'd like to figure out how
to harness this after I land it.

Since it's turned off by default, it should have no effect on behavior.

* CMakeLists.txt:
* JavaScriptCore.vcxproj/JavaScriptCore.vcxproj:
* JavaScriptCore.xcodeproj/project.pbxproj:
* dfg/DFGOSRExitFuzz.cpp: Added.
(JSC::numberOfOSRExitFuzzChecks):
* dfg/DFGOSRExitFuzz.h: Added.
* dfg/DFGSpeculativeJIT.cpp:
(JSC::DFG::SpeculativeJIT::emitGetArgumentStart):
(JSC::DFG::SpeculativeJIT::emitOSRExitFuzzCheck):
(JSC::DFG::SpeculativeJIT::speculationCheck):
* dfg/DFGSpeculativeJIT.h:
* ftl/FTLLowerDFGToLLVM.cpp:
(JSC::FTL::DFG::LowerDFGToLLVM::appendOSRExit):
* jsc.cpp:
(jscmain):
* runtime/Options.h:
* runtime/TestRunnerUtils.h:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@186252 268f45cc-cd09-0410-ab3c-d52691b4dbfc

12 files changed:
Source/JavaScriptCore/CMakeLists.txt
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/JavaScriptCore.vcxproj/JavaScriptCore.vcxproj
Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj
Source/JavaScriptCore/dfg/DFGOSRExitFuzz.cpp [new file with mode: 0644]
Source/JavaScriptCore/dfg/DFGOSRExitFuzz.h [new file with mode: 0644]
Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp
Source/JavaScriptCore/dfg/DFGSpeculativeJIT.h
Source/JavaScriptCore/ftl/FTLLowerDFGToLLVM.cpp
Source/JavaScriptCore/jsc.cpp
Source/JavaScriptCore/runtime/Options.h
Source/JavaScriptCore/runtime/TestRunnerUtils.h

index 011624c..f03a9a4 100644 (file)
@@ -208,6 +208,7 @@ set(JavaScriptCore_SOURCES
     dfg/DFGOSRExitCompiler32_64.cpp
     dfg/DFGOSRExitCompiler64.cpp
     dfg/DFGOSRExitCompilerCommon.cpp
+    dfg/DFGOSRExitFuzz.cpp
     dfg/DFGOSRExitJumpPlaceholder.cpp
     dfg/DFGOSRExitPreparation.cpp
     dfg/DFGObjectAllocationSinkingPhase.cpp
index 4709c38..3910ce7 100644 (file)
@@ -1,3 +1,34 @@
+2015-07-02  Filip Pizlo  <fpizlo@apple.com>
+
+        DFG and FTL should have an OSR exit fuzzer
+        https://bugs.webkit.org/show_bug.cgi?id=146562
+
+        Reviewed by Benjamin Poulain.
+        
+        Adds a basic OSR exit fuzzer to JSC. This isn't hooked into any test harnesses yet, but I
+        spot-checked it on v8-earley-boyer.js and so far found no bugs. I'd like to figure out how
+        to harness this after I land it.
+        
+        Since it's turned off by default, it should have no effect on behavior.
+
+        * CMakeLists.txt:
+        * JavaScriptCore.vcxproj/JavaScriptCore.vcxproj:
+        * JavaScriptCore.xcodeproj/project.pbxproj:
+        * dfg/DFGOSRExitFuzz.cpp: Added.
+        (JSC::numberOfOSRExitFuzzChecks):
+        * dfg/DFGOSRExitFuzz.h: Added.
+        * dfg/DFGSpeculativeJIT.cpp:
+        (JSC::DFG::SpeculativeJIT::emitGetArgumentStart):
+        (JSC::DFG::SpeculativeJIT::emitOSRExitFuzzCheck):
+        (JSC::DFG::SpeculativeJIT::speculationCheck):
+        * dfg/DFGSpeculativeJIT.h:
+        * ftl/FTLLowerDFGToLLVM.cpp:
+        (JSC::FTL::DFG::LowerDFGToLLVM::appendOSRExit):
+        * jsc.cpp:
+        (jscmain):
+        * runtime/Options.h:
+        * runtime/TestRunnerUtils.h:
+
 2015-07-02  Saam barati  <saambarati1@gmail.com>
 
         Rename "Deconstruction" to "Destructuring" throughout JSC
index 7162254..4bf5104 100644 (file)
     <ClCompile Include="..\dfg\DFGOSRExitCompiler32_64.cpp" />
     <ClCompile Include="..\dfg\DFGOSRExitCompiler64.cpp" />
     <ClCompile Include="..\dfg\DFGOSRExitCompilerCommon.cpp" />
+    <ClCompile Include="..\dfg\DFGOSRExitFuzz.cpp" />
     <ClCompile Include="..\dfg\DFGOSRExitJumpPlaceholder.cpp" />
     <ClCompile Include="..\dfg\DFGOSRExitPreparation.cpp" />
     <ClCompile Include="..\dfg\DFGObjectAllocationSinkingPhase.cpp" />
     <ClInclude Include="..\dfg\DFGOSRExitCompilationInfo.h" />
     <ClInclude Include="..\dfg\DFGOSRExitCompiler.h" />
     <ClInclude Include="..\dfg\DFGOSRExitCompilerCommon.h" />
+    <ClInclude Include="..\dfg\DFGOSRExitFuzz.h" />
     <ClInclude Include="..\dfg\DFGOSRExitJumpPlaceholder.h" />
     <ClInclude Include="..\dfg\DFGOSRExitPreparation.h" />
     <ClInclude Include="..\dfg\DFGPhantomInsertionPhase.h" />
index ad2f4c6..e03e763 100644 (file)
                0F38B01817CFE75500B144D3 /* DFGCompilationKey.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F38B01417CFE75500B144D3 /* DFGCompilationKey.h */; settings = {ATTRIBUTES = (Private, ); }; };
                0F38B01917CFE75500B144D3 /* DFGCompilationMode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F38B01517CFE75500B144D3 /* DFGCompilationMode.cpp */; };
                0F38B01A17CFE75500B144D3 /* DFGCompilationMode.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F38B01617CFE75500B144D3 /* DFGCompilationMode.h */; settings = {ATTRIBUTES = (Private, ); }; };
+               0F392C891B46188400844728 /* DFGOSRExitFuzz.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F392C871B46188400844728 /* DFGOSRExitFuzz.cpp */; };
+               0F392C8A1B46188400844728 /* DFGOSRExitFuzz.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F392C881B46188400844728 /* DFGOSRExitFuzz.h */; settings = {ATTRIBUTES = (Private, ); }; };
                0F3A1BF91A9ECB7D000DE01A /* DFGPutStackSinkingPhase.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F3A1BF71A9ECB7D000DE01A /* DFGPutStackSinkingPhase.cpp */; };
                0F3A1BFA1A9ECB7D000DE01A /* DFGPutStackSinkingPhase.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F3A1BF81A9ECB7D000DE01A /* DFGPutStackSinkingPhase.h */; settings = {ATTRIBUTES = (Private, ); }; };
                0F3AC752183EA1040032029F /* StackAlignment.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F3AC751183EA1040032029F /* StackAlignment.h */; settings = {ATTRIBUTES = (Private, ); }; };
                0F38B01417CFE75500B144D3 /* DFGCompilationKey.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DFGCompilationKey.h; path = dfg/DFGCompilationKey.h; sourceTree = "<group>"; };
                0F38B01517CFE75500B144D3 /* DFGCompilationMode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = DFGCompilationMode.cpp; path = dfg/DFGCompilationMode.cpp; sourceTree = "<group>"; };
                0F38B01617CFE75500B144D3 /* DFGCompilationMode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DFGCompilationMode.h; path = dfg/DFGCompilationMode.h; sourceTree = "<group>"; };
+               0F392C871B46188400844728 /* DFGOSRExitFuzz.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = DFGOSRExitFuzz.cpp; path = dfg/DFGOSRExitFuzz.cpp; sourceTree = "<group>"; };
+               0F392C881B46188400844728 /* DFGOSRExitFuzz.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DFGOSRExitFuzz.h; path = dfg/DFGOSRExitFuzz.h; sourceTree = "<group>"; };
                0F3A1BF71A9ECB7D000DE01A /* DFGPutStackSinkingPhase.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = DFGPutStackSinkingPhase.cpp; path = dfg/DFGPutStackSinkingPhase.cpp; sourceTree = "<group>"; };
                0F3A1BF81A9ECB7D000DE01A /* DFGPutStackSinkingPhase.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DFGPutStackSinkingPhase.h; path = dfg/DFGPutStackSinkingPhase.h; sourceTree = "<group>"; };
                0F3AC751183EA1040032029F /* StackAlignment.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StackAlignment.h; sourceTree = "<group>"; };
                                0FC0977014693AEF00CF2442 /* DFGOSRExitCompiler64.cpp */,
                                0F7025A71714B0F800382C0E /* DFGOSRExitCompilerCommon.cpp */,
                                0F7025A81714B0F800382C0E /* DFGOSRExitCompilerCommon.h */,
+                               0F392C871B46188400844728 /* DFGOSRExitFuzz.cpp */,
+                               0F392C881B46188400844728 /* DFGOSRExitFuzz.h */,
                                0FEFC9A71681A3B000567F53 /* DFGOSRExitJumpPlaceholder.cpp */,
                                0FEFC9A81681A3B000567F53 /* DFGOSRExitJumpPlaceholder.h */,
                                0F235BE917178E7300690C7F /* DFGOSRExitPreparation.cpp */,
                                A513E5CB185F9624007E95AD /* InjectedScriptManager.h in Headers */,
                                A5840E21187B7B8600843B10 /* InjectedScriptModule.h in Headers */,
                                A513E5C7185F9446007E95AD /* InjectedScriptSource.h in Headers */,
+                               0F392C8A1B46188400844728 /* DFGOSRExitFuzz.h in Headers */,
                                A5840E29187CA5E600843B10 /* inline-and-minify-stylesheets-and-scripts.py in Headers */,
                                0F24E55617F0B71C00ABB217 /* InlineCallFrameSet.h in Headers */,
                                99E45A2718A1B2590026D88F /* InputCursor.h in Headers */,
                                FE20CE9D15F04A9500DF3430 /* LLIntCLoop.cpp in Sources */,
                                0F4680D214BBD16500BFE272 /* LLIntData.cpp in Sources */,
                                0F38B01117CF078000B144D3 /* LLIntEntrypoint.cpp in Sources */,
+                               0F392C891B46188400844728 /* DFGOSRExitFuzz.cpp in Sources */,
                                0F4680A814BA7FAB00BFE272 /* LLIntExceptions.cpp in Sources */,
                                0FD949841A97DB9600E28966 /* JSFunctionNameScope.cpp in Sources */,
                                0F4680A414BA7F8D00BFE272 /* LLIntSlowPaths.cpp in Sources */,
diff --git a/Source/JavaScriptCore/dfg/DFGOSRExitFuzz.cpp b/Source/JavaScriptCore/dfg/DFGOSRExitFuzz.cpp
new file mode 100644 (file)
index 0000000..e27fd36
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
+ */
+
+#include "config.h"
+#include "DFGOSRExitFuzz.h"
+
+#include "TestRunnerUtils.h"
+
+namespace JSC { namespace DFG {
+
+unsigned g_numberOfOSRExitFuzzChecks;
+
+} // namespace DFG
+
+unsigned numberOfOSRExitFuzzChecks()
+{
+    return DFG::g_numberOfOSRExitFuzzChecks;
+}
+
+} // namespace JSC
+
+
diff --git a/Source/JavaScriptCore/dfg/DFGOSRExitFuzz.h b/Source/JavaScriptCore/dfg/DFGOSRExitFuzz.h
new file mode 100644 (file)
index 0000000..215c166
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
+ */
+
+#ifndef DFGOSRExitFuzz_h
+#define DFGOSRExitFuzz_h
+
+namespace JSC { namespace DFG {
+
+// DFG- and FTL-generated code will query this on every speculation.
+extern unsigned g_numberOfOSRExitFuzzChecks;
+
+} } // namespace JSC::DFG
+
+#endif // DFGOSRExitFuzz_h
+
index 98db3e0..6650b33 100644 (file)
@@ -34,6 +34,7 @@
 #include "DFGCallArrayAllocatorSlowPathGenerator.h"
 #include "DFGCallCreateDirectArgumentsSlowPathGenerator.h"
 #include "DFGMayExit.h"
+#include "DFGOSRExitFuzz.h"
 #include "DFGSaneStringGetByValSlowPathGenerator.h"
 #include "DFGSlowPathGenerator.h"
 #include "DirectArguments.h"
@@ -156,12 +157,53 @@ void SpeculativeJIT::emitGetArgumentStart(CodeOrigin origin, GPRReg startGPR)
         GPRInfo::callFrameRegister, startGPR);
 }
 
+MacroAssembler::Jump SpeculativeJIT::emitOSRExitFuzzCheck()
+{
+    if (!Options::enableOSRExitFuzz())
+        return MacroAssembler::Jump();
+    
+    MacroAssembler::Jump result;
+    
+    m_jit.pushToSave(GPRInfo::regT0);
+    m_jit.load32(&g_numberOfOSRExitFuzzChecks, GPRInfo::regT0);
+    m_jit.add32(TrustedImm32(1), GPRInfo::regT0);
+    m_jit.store32(GPRInfo::regT0, &g_numberOfOSRExitFuzzChecks);
+    unsigned atOrAfter = Options::fireOSRExitFuzzAtOrAfter();
+    unsigned at = Options::fireOSRExitFuzzAt();
+    if (at || atOrAfter) {
+        unsigned threshold;
+        MacroAssembler::RelationalCondition condition;
+        if (atOrAfter) {
+            threshold = atOrAfter;
+            condition = MacroAssembler::Below;
+        } else {
+            threshold = at;
+            condition = MacroAssembler::NotEqual;
+        }
+        MacroAssembler::Jump ok = m_jit.branch32(
+            condition, GPRInfo::regT0, MacroAssembler::TrustedImm32(threshold));
+        m_jit.popToRestore(GPRInfo::regT0);
+        result = m_jit.jump();
+        ok.link(&m_jit);
+    }
+    m_jit.popToRestore(GPRInfo::regT0);
+    
+    return result;
+}
+
 void SpeculativeJIT::speculationCheck(ExitKind kind, JSValueSource jsValueSource, Node* node, MacroAssembler::Jump jumpToFail)
 {
     if (!m_compileOkay)
         return;
     ASSERT(m_isCheckingArgumentTypes || m_canExit);
-    m_jit.appendExitInfo(jumpToFail);
+    JITCompiler::Jump fuzzJump = emitOSRExitFuzzCheck();
+    if (fuzzJump.isSet()) {
+        JITCompiler::JumpList jumpsToFail;
+        jumpsToFail.append(fuzzJump);
+        jumpsToFail.append(jumpToFail);
+        m_jit.appendExitInfo(jumpsToFail);
+    } else
+        m_jit.appendExitInfo(jumpToFail);
     m_jit.jitCode()->appendOSRExit(OSRExit(kind, jsValueSource, m_jit.graph().methodOfGettingAValueProfileFor(node), this, m_stream->size()));
 }
 
@@ -170,7 +212,14 @@ void SpeculativeJIT::speculationCheck(ExitKind kind, JSValueSource jsValueSource
     if (!m_compileOkay)
         return;
     ASSERT(m_isCheckingArgumentTypes || m_canExit);
-    m_jit.appendExitInfo(jumpsToFail);
+    JITCompiler::Jump fuzzJump = emitOSRExitFuzzCheck();
+    if (fuzzJump.isSet()) {
+        JITCompiler::JumpList myJumpsToFail;
+        myJumpsToFail.append(jumpsToFail);
+        myJumpsToFail.append(fuzzJump);
+        m_jit.appendExitInfo(myJumpsToFail);
+    } else
+        m_jit.appendExitInfo(jumpsToFail);
     m_jit.jitCode()->appendOSRExit(OSRExit(kind, jsValueSource, m_jit.graph().methodOfGettingAValueProfileFor(node), this, m_stream->size()));
 }
 
index 5d219da..8798b6d 100644 (file)
@@ -2341,6 +2341,10 @@ public:
     void emitGetCallee(CodeOrigin, GPRReg calleeGPR);
     void emitGetArgumentStart(CodeOrigin, GPRReg startGPR);
     
+    // Generate an OSR exit fuzz check. Returns Jump() if OSR exit fuzz is not enabled, or if
+    // it's in training mode.
+    MacroAssembler::Jump emitOSRExitFuzzCheck();
+    
     // Add a speculation check.
     void speculationCheck(ExitKind, JSValueSource, Node*, MacroAssembler::Jump jumpToFail);
     void speculationCheck(ExitKind, JSValueSource, Node*, const MacroAssembler::JumpList& jumpsToFail);
index d5ce0d7..ce17ab4 100644 (file)
@@ -32,6 +32,7 @@
 #include "DFGAbstractInterpreterInlines.h"
 #include "DFGInPlaceAbstractState.h"
 #include "DFGOSRAvailabilityAnalysisPhase.h"
+#include "DFGOSRExitFuzz.h"
 #include "DirectArguments.h"
 #include "FTLAbstractHeapRepository.h"
 #include "FTLAvailableRecovery.h"
@@ -8165,6 +8166,25 @@ private:
             if (!m_availableRecoveries.isEmpty())
                 dataLog("        Available recoveries: ", listDump(m_availableRecoveries), "\n");
         }
+        
+        if (Options::enableOSRExitFuzz()) {
+            LValue numberOfFuzzChecks = m_out.add(
+                m_out.load32(m_out.absolute(&g_numberOfOSRExitFuzzChecks)),
+                m_out.int32One);
+            
+            m_out.store32(numberOfFuzzChecks, m_out.absolute(&g_numberOfOSRExitFuzzChecks));
+            
+            if (unsigned atOrAfter = Options::fireOSRExitFuzzAtOrAfter()) {
+                failCondition = m_out.bitOr(
+                    failCondition,
+                    m_out.aboveOrEqual(numberOfFuzzChecks, m_out.constInt32(atOrAfter)));
+            }
+            if (unsigned at = Options::fireOSRExitFuzzAt()) {
+                failCondition = m_out.bitOr(
+                    failCondition,
+                    m_out.equal(numberOfFuzzChecks, m_out.constInt32(at)));
+            }
+        }
 
         ASSERT(m_ftlState.jitCode->osrExit.size() == m_ftlState.finalizer->osrExit.size());
         
index f300d1d..380d89b 100644 (file)
@@ -1551,6 +1551,8 @@ int jscmain(int argc, char** argv)
             Options::fireExecutableAllocationFuzzAt() || Options::fireExecutableAllocationFuzzAtOrAfter();
         if (Options::enableExecutableAllocationFuzz() && (!fireAtEnabled || Options::verboseExecutableAllocationFuzz()))
             printf("JSC EXECUTABLE ALLOCATION FUZZ: encountered %u checks.\n", numberOfExecutableAllocationFuzzChecks());
+        if (Options::enableOSRExitFuzz())
+            printf("JSC OSR EXIT FUZZ: encountered %u checks.\n", numberOfOSRExitFuzzChecks());
 #endif
     }
     
index fd1682c..19feb7e 100644 (file)
@@ -309,6 +309,10 @@ typedef const char* optionString;
     v(unsigned, fireExecutableAllocationFuzzAtOrAfter, 0, nullptr) \
     v(bool, verboseExecutableAllocationFuzz, false, nullptr) \
     \
+    v(bool, enableOSRExitFuzz, false, nullptr) \
+    v(unsigned, fireOSRExitFuzzAt, 0, nullptr) \
+    v(unsigned, fireOSRExitFuzzAtOrAfter, 0, nullptr) \
+    \
     v(bool, enableDollarVM, false, "installs the $vm debugging tool in global objects") \
     v(optionString, functionOverrides, nullptr, "file with debugging overrides for function bodies") \
 
index 4ca16b5..e6e702e 100644 (file)
@@ -46,6 +46,7 @@ JS_EXPORT_PRIVATE JSValue optimizeNextInvocation(ExecState*);
 
 JS_EXPORT_PRIVATE unsigned numberOfExceptionFuzzChecks();
 JS_EXPORT_PRIVATE unsigned numberOfExecutableAllocationFuzzChecks();
+JS_EXPORT_PRIVATE unsigned numberOfOSRExitFuzzChecks();
 
 } // namespace JSC