<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[191130] trunk/Source/JavaScriptCore</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/191130">191130</a></dd>
<dt>Author</dt> <dd>mark.lam@apple.com</dd>
<dt>Date</dt> <dd>2015-10-15 12:54:02 -0700 (Thu, 15 Oct 2015)</dd>
</dl>

<h3>Log Message</h3>
<pre>Add MASM_PROBE support for ARM64.
https://bugs.webkit.org/show_bug.cgi?id=150128

Reviewed by Michael Saboff.

* JavaScriptCore.xcodeproj/project.pbxproj:
* assembler/ARM64Assembler.h:
- Convert the ARM64 registers enum list into a macro list so that we can use
  it elsewhere e.g. to declare fields in the probe CPUState.
  Also de-tabbed the contents of the ARM64Registers namespace since the enum
  list change touches almost all of it anyway. This reduces the amount of
  complaints from the style checker.

* assembler/AbstractMacroAssembler.h:
(JSC::AbstractMacroAssembler::CPUState::registerName):
(JSC::AbstractMacroAssembler::CPUState::registerValue):
- Change CPUState methods to allow for registers ID that do not map to one of
  its fields. This is needed because ARM64's registers include aliases for some
  register names. The CPUState will not allocate separate storage for the
  aliases. 

* assembler/MacroAssemblerARM64.cpp: Added.
(JSC::arm64ProbeTrampoline):
- Unlike the probe mechanism for other CPUs, the ARM64 implementation does not
  allow the probe function to modify the sp and pc registers.  We insert this
  wrapper function between ctiMasmProbeTrampoline() and the user's probe function
  so that we can check if the user tried to modify sp and pc.  If so, we will
  print an error message so that we can alert the user that we don't support
  that on ARM64.

  See the comment in ctiMasmProbeTrampoline() in JITStubsARM64.h for details
  on why we cannot support sp and pc modifications by the probe function.

(JSC::MacroAssemblerARM64::probe):

* assembler/MacroAssemblerARM64.h:
(JSC::MacroAssemblerARM64::repatchCall):
(JSC::MacroAssemblerARM64::makeBranch):
* jit/JITStubs.cpp:
* jit/JITStubsARM64.h: Added.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceJavaScriptCoreChangeLog">trunk/Source/JavaScriptCore/ChangeLog</a></li>
<li><a href="#trunkSourceJavaScriptCoreJavaScriptCorexcodeprojprojectpbxproj">trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceJavaScriptCoreassemblerARM64Assemblerh">trunk/Source/JavaScriptCore/assembler/ARM64Assembler.h</a></li>
<li><a href="#trunkSourceJavaScriptCoreassemblerAbstractMacroAssemblerh">trunk/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h</a></li>
<li><a href="#trunkSourceJavaScriptCoreassemblerMacroAssemblerARM64h">trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.h</a></li>
<li><a href="#trunkSourceJavaScriptCorejitJITStubscpp">trunk/Source/JavaScriptCore/jit/JITStubs.cpp</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceJavaScriptCoreassemblerMacroAssemblerARM64cpp">trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.cpp</a></li>
<li><a href="#trunkSourceJavaScriptCorejitJITStubsARM64h">trunk/Source/JavaScriptCore/jit/JITStubsARM64.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceJavaScriptCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/ChangeLog (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/ChangeLog        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/ChangeLog        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -1,5 +1,48 @@
</span><span class="cx"> 2015-10-15  Mark Lam  &lt;mark.lam@apple.com&gt;
</span><span class="cx"> 
</span><ins>+        Add MASM_PROBE support for ARM64.
+        https://bugs.webkit.org/show_bug.cgi?id=150128
+
+        Reviewed by Michael Saboff.
+
+        * JavaScriptCore.xcodeproj/project.pbxproj:
+        * assembler/ARM64Assembler.h:
+        - Convert the ARM64 registers enum list into a macro list so that we can use
+          it elsewhere e.g. to declare fields in the probe CPUState.
+          Also de-tabbed the contents of the ARM64Registers namespace since the enum
+          list change touches almost all of it anyway. This reduces the amount of
+          complaints from the style checker.
+
+        * assembler/AbstractMacroAssembler.h:
+        (JSC::AbstractMacroAssembler::CPUState::registerName):
+        (JSC::AbstractMacroAssembler::CPUState::registerValue):
+        - Change CPUState methods to allow for registers ID that do not map to one of
+          its fields. This is needed because ARM64's registers include aliases for some
+          register names. The CPUState will not allocate separate storage for the
+          aliases. 
+
+        * assembler/MacroAssemblerARM64.cpp: Added.
+        (JSC::arm64ProbeTrampoline):
+        - Unlike the probe mechanism for other CPUs, the ARM64 implementation does not
+          allow the probe function to modify the sp and pc registers.  We insert this
+          wrapper function between ctiMasmProbeTrampoline() and the user's probe function
+          so that we can check if the user tried to modify sp and pc.  If so, we will
+          print an error message so that we can alert the user that we don't support
+          that on ARM64.
+
+          See the comment in ctiMasmProbeTrampoline() in JITStubsARM64.h for details
+          on why we cannot support sp and pc modifications by the probe function.
+
+        (JSC::MacroAssemblerARM64::probe):
+
+        * assembler/MacroAssemblerARM64.h:
+        (JSC::MacroAssemblerARM64::repatchCall):
+        (JSC::MacroAssemblerARM64::makeBranch):
+        * jit/JITStubs.cpp:
+        * jit/JITStubsARM64.h: Added.
+
+2015-10-15  Mark Lam  &lt;mark.lam@apple.com&gt;
+
</ins><span class="cx">         Fix some typos in comments.
</span><span class="cx">         https://bugs.webkit.org/show_bug.cgi?id=150181
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceJavaScriptCoreJavaScriptCorexcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -1792,6 +1792,8 @@
</span><span class="cx">                 FE7C41961B97FC4B00F4D598 /* PingPongStackOverflowTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FEDA50D41B97F442009A3B4F /* PingPongStackOverflowTest.cpp */; };
</span><span class="cx">                 FEA08620182B7A0400F6D851 /* Breakpoint.h in Headers */ = {isa = PBXBuildFile; fileRef = FEA0861E182B7A0400F6D851 /* Breakpoint.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="cx">                 FEA08621182B7A0400F6D851 /* DebuggerPrimitives.h in Headers */ = {isa = PBXBuildFile; fileRef = FEA0861F182B7A0400F6D851 /* DebuggerPrimitives.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><ins>+                FEB137551BB0C6AD00CD5100 /* JITStubsARM64.h in Headers */ = {isa = PBXBuildFile; fileRef = FEB137541BB0C68A00CD5100 /* JITStubsARM64.h */; settings = {ASSET_TAGS = (); }; };
+                FEB137571BB11EF900CD5100 /* MacroAssemblerARM64.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FEB137561BB11EEE00CD5100 /* MacroAssemblerARM64.cpp */; settings = {ASSET_TAGS = (); }; };
</ins><span class="cx">                 FEB51F6C1A97B688001F921C /* Regress141809.mm in Sources */ = {isa = PBXBuildFile; fileRef = FEB51F6B1A97B688001F921C /* Regress141809.mm */; };
</span><span class="cx">                 FEB58C14187B8B160098EF0B /* ErrorHandlingScope.cpp in Sources */ = {isa = PBXBuildFile; fileRef = FEB58C12187B8B160098EF0B /* ErrorHandlingScope.cpp */; };
</span><span class="cx">                 FEB58C15187B8B160098EF0B /* ErrorHandlingScope.h in Headers */ = {isa = PBXBuildFile; fileRef = FEB58C13187B8B160098EF0B /* ErrorHandlingScope.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="lines">@@ -3725,6 +3727,8 @@
</span><span class="cx">                 FE98B5B61BB9AE110073E7A6 /* JITSubGenerator.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JITSubGenerator.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 FEA0861E182B7A0400F6D851 /* Breakpoint.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Breakpoint.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 FEA0861F182B7A0400F6D851 /* DebuggerPrimitives.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DebuggerPrimitives.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                FEB137541BB0C68A00CD5100 /* JITStubsARM64.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JITStubsARM64.h; sourceTree = &quot;&lt;group&gt;&quot;; };
+                FEB137561BB11EEE00CD5100 /* MacroAssemblerARM64.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MacroAssemblerARM64.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 FEB51F6A1A97B688001F921C /* Regress141809.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Regress141809.h; path = API/tests/Regress141809.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 FEB51F6B1A97B688001F921C /* Regress141809.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = Regress141809.mm; path = API/tests/Regress141809.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 FEB58C12187B8B160098EF0B /* ErrorHandlingScope.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ErrorHandlingScope.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -4204,6 +4208,7 @@
</span><span class="cx">                                 14A23D6C0F4E19CE0023CDAD /* JITStubs.cpp */,
</span><span class="cx">                                 14A6581A0F4E36F4000150FD /* JITStubs.h */,
</span><span class="cx">                                 FEF6835A174343CC00A32E25 /* JITStubsARM.h */,
</span><ins>+                                FEB137541BB0C68A00CD5100 /* JITStubsARM64.h */,
</ins><span class="cx">                                 FEF6835B174343CC00A32E25 /* JITStubsARMv7.h */,
</span><span class="cx">                                 FEF6835D174343CC00A32E25 /* JITStubsX86.h */,
</span><span class="cx">                                 FEF6835C174343CC00A32E25 /* JITStubsX86_64.h */,
</span><span class="lines">@@ -5576,6 +5581,7 @@
</span><span class="cx">                                 86C36EE90EE1289D00B3DF59 /* MacroAssembler.h */,
</span><span class="cx">                                 86C568DD11A213EE0007F7F0 /* MacroAssemblerARM.cpp */,
</span><span class="cx">                                 86D3B2C210156BDE002865E7 /* MacroAssemblerARM.h */,
</span><ins>+                                FEB137561BB11EEE00CD5100 /* MacroAssemblerARM64.cpp */,
</ins><span class="cx">                                 8640923C156EED3B00566CB2 /* MacroAssemblerARM64.h */,
</span><span class="cx">                                 A729009B17976C6000317298 /* MacroAssemblerARMv7.cpp */,
</span><span class="cx">                                 86ADD1440FDDEA980006EEC2 /* MacroAssemblerARMv7.h */,
</span><span class="lines">@@ -6358,6 +6364,7 @@
</span><span class="cx">                                 0FEA0A241709606900BB722C /* FTLIntrinsicRepository.h in Headers */,
</span><span class="cx">                                 0FEA0A0E170513DB00BB722C /* FTLJITCode.h in Headers */,
</span><span class="cx">                                 A78A9781179738D5009DF744 /* FTLJITFinalizer.h in Headers */,
</span><ins>+                                FEB137551BB0C6AD00CD5100 /* JITStubsARM64.h in Headers */,
</ins><span class="cx">                                 0F6B1CB6185FC9E900845D97 /* FTLJSCall.h in Headers */,
</span><span class="cx">                                 0FD120301A8AED12000F5280 /* FTLJSCallBase.h in Headers */,
</span><span class="cx">                                 0FD120341A8C85BD000F5280 /* FTLJSCallVarargs.h in Headers */,
</span><span class="lines">@@ -7487,6 +7494,7 @@
</span><span class="cx">                                 0F63945415D07055006A597C /* ArrayProfile.cpp in Sources */,
</span><span class="cx">                                 147F39C0107EC37600427A48 /* ArrayPrototype.cpp in Sources */,
</span><span class="cx">                                 0F24E54017EA9F5900ABB217 /* AssemblyHelpers.cpp in Sources */,
</span><ins>+                                FEB137571BB11EF900CD5100 /* MacroAssemblerARM64.cpp in Sources */,
</ins><span class="cx">                                 52678F8E1A031009006A306D /* BasicBlockLocation.cpp in Sources */,
</span><span class="cx">                                 0F64B2711A784BAF006E4E66 /* BinarySwitch.cpp in Sources */,
</span><span class="cx">                                 14280863107EC11A0013E7B2 /* BooleanConstructor.cpp in Sources */,
</span></span></pre></div>
<a id="trunkSourceJavaScriptCoreassemblerARM64Assemblerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/assembler/ARM64Assembler.h (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/assembler/ARM64Assembler.h        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/assembler/ARM64Assembler.h        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -388,91 +388,124 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> namespace ARM64Registers {
</span><del>-    typedef enum {
-        // Parameter/result registers
-        x0,
-        x1,
-        x2,
-        x3,
-        x4,
-        x5,
-        x6,
-        x7,
-        // Indirect result location register
-        x8,
-        // Temporary registers
-        x9,
-        x10,
-        x11,
-        x12,
-        x13,
-        x14,
-        x15,
-        // Intra-procedure-call scratch registers (temporary)
-        x16, ip0 = x16,
-        x17, ip1 = x17,
-        // Platform Register (temporary)
-        x18,
-        // Callee-saved
-        x19,
-        x20,
-        x21,
-        x22,
-        x23,
-        x24,
-        x25,
-        x26,
-        x27,
-        x28,
-        // Special
-        x29, fp = x29,
-        x30, lr = x30,
-        sp,
-        zr = 0x3f,
-    } RegisterID;
</del><span class="cx"> 
</span><del>-    typedef enum {
-        // Parameter/result registers
-        q0,
-        q1,
-        q2,
-        q3,
-        q4,
-        q5,
-        q6,
-        q7,
-        // Callee-saved (up to 64-bits only!)
-        q8,
-        q9,
-        q10,
-        q11,
-        q12,
-        q13,
-        q14,
-        q15,
-        // Temporary registers
-        q16,
-        q17,
-        q18,
-        q19,
-        q20,
-        q21,
-        q22,
-        q23,
-        q24,
-        q25,
-        q26,
-        q27,
-        q28,
-        q29,
-        q30,
-        q31,
-    } FPRegisterID;
</del><ins>+#define FOR_EACH_CPU_REGISTER(V) \
+    FOR_EACH_CPU_GPREGISTER(V) \
+    FOR_EACH_CPU_SPECIAL_REGISTER(V) \
+    FOR_EACH_CPU_FPREGISTER(V)
</ins><span class="cx"> 
</span><del>-    static constexpr bool isSp(RegisterID reg) { return reg == sp; }
-    static constexpr bool isZr(RegisterID reg) { return reg == zr; }
-}
</del><ins>+// The following are defined as pairs of the following value:
+// 1. type of the storage needed to save the register value by the JIT probe.
+// 2. name of the register.
+#define FOR_EACH_CPU_GPREGISTER(V) \
+    /* Parameter/result registers */ \
+    V(void*, x0) \
+    V(void*, x1) \
+    V(void*, x2) \
+    V(void*, x3) \
+    V(void*, x4) \
+    V(void*, x5) \
+    V(void*, x6) \
+    V(void*, x7) \
+    /* Indirect result location register */ \
+    V(void*, x8) \
+    /* Temporary registers */ \
+    V(void*, x9) \
+    V(void*, x10) \
+    V(void*, x11) \
+    V(void*, x12) \
+    V(void*, x13) \
+    V(void*, x14) \
+    V(void*, x15) \
+    /* Intra-procedure-call scratch registers (temporary) */ \
+    V(void*, x16) \
+    V(void*, x17) \
+    /* Platform Register (temporary) */ \
+    V(void*, x18) \
+    /* Callee-saved */ \
+    V(void*, x19) \
+    V(void*, x20) \
+    V(void*, x21) \
+    V(void*, x22) \
+    V(void*, x23) \
+    V(void*, x24) \
+    V(void*, x25) \
+    V(void*, x26) \
+    V(void*, x27) \
+    V(void*, x28) \
+    /* Special */ \
+    V(void*, fp) \
+    V(void*, lr) \
+    V(void*, sp)
</ins><span class="cx"> 
</span><ins>+#define FOR_EACH_CPU_SPECIAL_REGISTER(V) \
+    V(void*, pc) \
+    V(void*, nzcv) \
+    V(void*, fpsr) \
+
+// ARM64 always has 32 FPU registers 128-bits each. See http://llvm.org/devmtg/2012-11/Northover-AArch64.pdf
+// and Section 5.1.2 in http://infocenter.arm.com/help/topic/com.arm.doc.ihi0055b/IHI0055B_aapcs64.pdf.
+// However, we only use them for 64-bit doubles.
+#define FOR_EACH_CPU_FPREGISTER(V) \
+    /* Parameter/result registers */ \
+    V(double, q0) \
+    V(double, q1) \
+    V(double, q2) \
+    V(double, q3) \
+    V(double, q4) \
+    V(double, q5) \
+    V(double, q6) \
+    V(double, q7) \
+    /* Callee-saved (up to 64-bits only!) */ \
+    V(double, q8) \
+    V(double, q9) \
+    V(double, q10) \
+    V(double, q11) \
+    V(double, q12) \
+    V(double, q13) \
+    V(double, q14) \
+    V(double, q15) \
+    /* Temporary registers */ \
+    V(double, q16) \
+    V(double, q17) \
+    V(double, q18) \
+    V(double, q19) \
+    V(double, q20) \
+    V(double, q21) \
+    V(double, q22) \
+    V(double, q23) \
+    V(double, q24) \
+    V(double, q25) \
+    V(double, q26) \
+    V(double, q27) \
+    V(double, q28) \
+    V(double, q29) \
+    V(double, q30) \
+    V(double, q31)
+
+typedef enum {
+    #define DECLARE_REGISTER(_type, _regName) _regName,
+    FOR_EACH_CPU_GPREGISTER(DECLARE_REGISTER)
+    #undef DECLARE_REGISTER
+
+    ip0 = x16,
+    ip1 = x17,
+    x29 = fp,
+    x30 = lr,
+    zr = 0x3f,
+} RegisterID;
+
+typedef enum {
+    #define DECLARE_REGISTER(_type, _regName) _regName,
+    FOR_EACH_CPU_FPREGISTER(DECLARE_REGISTER)
+    #undef DECLARE_REGISTER
+} FPRegisterID;
+
+static constexpr bool isSp(RegisterID reg) { return reg == sp; }
+static constexpr bool isZr(RegisterID reg) { return reg == zr; }
+
+} // namespace ARM64Registers
+
</ins><span class="cx"> class ARM64Assembler {
</span><span class="cx"> public:
</span><span class="cx">     typedef ARM64Registers::RegisterID RegisterID;
</span></span></pre></div>
<a id="trunkSourceJavaScriptCoreassemblerAbstractMacroAssemblerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -860,8 +860,9 @@
</span><span class="cx">                     return #_regName;
</span><span class="cx">                 FOR_EACH_CPU_GPREGISTER(DECLARE_REGISTER)
</span><span class="cx">                 #undef DECLARE_REGISTER
</span><ins>+            default:
+                RELEASE_ASSERT_NOT_REACHED();
</ins><span class="cx">             }
</span><del>-            RELEASE_ASSERT_NOT_REACHED();
</del><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">         static const char* fprName(FPRegisterID regID)
</span><span class="lines">@@ -872,8 +873,9 @@
</span><span class="cx">                     return #_regName;
</span><span class="cx">                 FOR_EACH_CPU_FPREGISTER(DECLARE_REGISTER)
</span><span class="cx">                 #undef DECLARE_REGISTER
</span><ins>+            default:
+                RELEASE_ASSERT_NOT_REACHED();
</ins><span class="cx">             }
</span><del>-            RELEASE_ASSERT_NOT_REACHED();
</del><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">         void* gpr(RegisterID regID)
</span><span class="lines">@@ -884,8 +886,9 @@
</span><span class="cx">                     return _regName;
</span><span class="cx">                 FOR_EACH_CPU_GPREGISTER(DECLARE_REGISTER)
</span><span class="cx">                 #undef DECLARE_REGISTER
</span><ins>+            default:
+                RELEASE_ASSERT_NOT_REACHED();
</ins><span class="cx">             }
</span><del>-            RELEASE_ASSERT_NOT_REACHED();
</del><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">         double fpr(FPRegisterID regID)
</span><span class="lines">@@ -896,8 +899,9 @@
</span><span class="cx">                     return _regName;
</span><span class="cx">                 FOR_EACH_CPU_FPREGISTER(DECLARE_REGISTER)
</span><span class="cx">                 #undef DECLARE_REGISTER
</span><ins>+            default:
+                RELEASE_ASSERT_NOT_REACHED();
</ins><span class="cx">             }
</span><del>-            RELEASE_ASSERT_NOT_REACHED();
</del><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">     };
</span></span></pre></div>
<a id="trunkSourceJavaScriptCoreassemblerMacroAssemblerARM64cpp"></a>
<div class="addfile"><h4>Added: trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.cpp (0 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.cpp                                (rev 0)
+++ trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.cpp        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -0,0 +1,92 @@
</span><ins>+/*
+ * Copyright (C) 2013-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 &quot;config.h&quot;
+
+#if ENABLE(ASSEMBLER) &amp;&amp; CPU(ARM64)
+#include &quot;MacroAssemblerARM64.h&quot;
+
+namespace JSC {
+
+#if ENABLE(MASM_PROBE)
+
+extern &quot;C&quot; void ctiMasmProbeTrampoline();
+
+using namespace ARM64Registers;
+
+static void arm64ProbeTrampoline(MacroAssemblerARM64::ProbeContext* context)
+{
+    void* origSP = context-&gt;cpu.sp;
+    void* origPC = context-&gt;cpu.pc;
+    
+    context-&gt;probeFunction(context);
+    
+    if (context-&gt;cpu.sp != origSP) {
+        dataLog(&quot;MacroAssembler probe ERROR: ARM64 does not support the probe changing the SP. The change will be ignored\n&quot;);
+        context-&gt;cpu.sp = origSP;
+    }
+    if (context-&gt;cpu.pc != origPC) {
+        dataLog(&quot;MacroAssembler probe ERROR: ARM64 does not support the probe changing the PC. The change will be ignored\n&quot;);
+        context-&gt;cpu.pc = origPC;
+    }
+}
+
+// For details on &quot;What code is emitted for the probe?&quot; and &quot;What values are in
+// the saved registers?&quot;, see comment for MacroAssemblerX86Common::probe() in
+// MacroAssemblerX86Common.cpp.
+void MacroAssemblerARM64::probe(MacroAssemblerARM64::ProbeFunction function, void* arg1, void* arg2)
+{
+    sub64(TrustedImm32(8 * 8), sp);
+
+    store64(x27, Address(sp, 4 * 8));
+    store64(x28, Address(sp, 5 * 8));
+    store64(lr, Address(sp, 6 * 8));
+
+    add64(TrustedImm32(8 * 8), sp, x28);
+    store64(x28, Address(sp, 7 * 8)); // Save original sp value.
+
+    move(TrustedImmPtr(reinterpret_cast&lt;void*&gt;(function)), x28);
+    store64(x28, Address(sp));
+    move(TrustedImmPtr(arg1), x28);
+    store64(x28, Address(sp, 1 * 8));
+    move(TrustedImmPtr(arg2), x28);
+    store64(x28, Address(sp, 2 * 8));
+    move(TrustedImmPtr(reinterpret_cast&lt;void*&gt;(arm64ProbeTrampoline)), x28);
+    store64(x28, Address(sp, 3 * 8));
+
+    move(TrustedImmPtr(reinterpret_cast&lt;void*&gt;(ctiMasmProbeTrampoline)), x28);
+    m_assembler.blr(x28);
+
+    // ctiMasmProbeTrampoline should have restored every register except for
+    // lr and the sp.
+    load64(Address(sp, 6 * 8), lr);
+    add64(TrustedImm32(8 * 8), sp);
+}
+#endif // ENABLE(MASM_PROBE)
+
+} // namespace JSC
+
+#endif // ENABLE(ASSEMBLER) &amp;&amp; CPU(ARM64)
+
</ins></span></pre></div>
<a id="trunkSourceJavaScriptCoreassemblerMacroAssemblerARM64h"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.h (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.h        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/assembler/MacroAssemblerARM64.h        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -2529,6 +2529,10 @@
</span><span class="cx">         ARM64Assembler::repatchPointer(call.dataLabelPtrAtOffset(REPATCH_OFFSET_CALL_TO_POINTER).dataLocation(), destination.executableAddress());
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+#if ENABLE(MASM_PROBE)
+    void probe(ProbeFunction, void* arg1 = 0, void* arg2 = 0);
+#endif // ENABLE(MASM_PROBE)
+
</ins><span class="cx"> protected:
</span><span class="cx">     ALWAYS_INLINE Jump makeBranch(ARM64Assembler::Condition cond)
</span><span class="cx">     {
</span></span></pre></div>
<a id="trunkSourceJavaScriptCorejitJITStubscpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/JavaScriptCore/jit/JITStubs.cpp (191129 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/jit/JITStubs.cpp        2015-10-15 19:52:34 UTC (rev 191129)
+++ trunk/Source/JavaScriptCore/jit/JITStubs.cpp        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -40,12 +40,12 @@
</span><span class="cx"> #include &quot;JITStubsARM.h&quot;
</span><span class="cx"> #elif CPU(ARM_THUMB2)
</span><span class="cx"> #include &quot;JITStubsARMv7.h&quot;
</span><ins>+#elif CPU(ARM64)
+#include &quot;JITStubsARM64.h&quot;
</ins><span class="cx"> #elif CPU(X86)
</span><span class="cx"> #include &quot;JITStubsX86.h&quot;
</span><span class="cx"> #elif CPU(X86_64)
</span><span class="cx"> #include &quot;JITStubsX86_64.h&quot;
</span><del>-#elif CPU(ARM64)
-// There isn't an ARM64 specific .h file
</del><span class="cx"> #elif CPU(MIPS)
</span><span class="cx"> // There isn't a MIPS specific .h file
</span><span class="cx"> #elif CPU(SH4)
</span></span></pre></div>
<a id="trunkSourceJavaScriptCorejitJITStubsARM64h"></a>
<div class="addfile"><h4>Added: trunk/Source/JavaScriptCore/jit/JITStubsARM64.h (0 => 191130)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/JavaScriptCore/jit/JITStubsARM64.h                                (rev 0)
+++ trunk/Source/JavaScriptCore/jit/JITStubsARM64.h        2015-10-15 19:54:02 UTC (rev 191130)
</span><span class="lines">@@ -0,0 +1,457 @@
</span><ins>+/*
+ * 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 JITStubsARM64_h
+#define JITStubsARM64_h
+
+#if !USE(JSVALUE64)
+#error &quot;JITStubsARM64.h only implements USE(JSVALUE64)&quot;
+#endif
+
+namespace JSC {
+
+#if COMPILER(GCC_OR_CLANG)
+
+#if ENABLE(MASM_PROBE)
+// The following are offsets for MacroAssembler::ProbeContext fields accessed
+// by the ctiMasmProbeTrampoline stub.
+
+#define PTR_SIZE 8
+#define PROBE_PROBE_FUNCTION_OFFSET (0 * PTR_SIZE)
+#define PROBE_ARG1_OFFSET (1 * PTR_SIZE)
+#define PROBE_ARG2_OFFSET (2 * PTR_SIZE)
+
+#define PROBE_FIRST_GPREG_OFFSET (3 * PTR_SIZE)
+
+#define GPREG_SIZE 8
+#define PROBE_CPU_X0_OFFSET (PROBE_FIRST_GPREG_OFFSET + (0 * GPREG_SIZE))
+#define PROBE_CPU_X1_OFFSET (PROBE_FIRST_GPREG_OFFSET + (1 * GPREG_SIZE))
+#define PROBE_CPU_X2_OFFSET (PROBE_FIRST_GPREG_OFFSET + (2 * GPREG_SIZE))
+#define PROBE_CPU_X3_OFFSET (PROBE_FIRST_GPREG_OFFSET + (3 * GPREG_SIZE))
+#define PROBE_CPU_X4_OFFSET (PROBE_FIRST_GPREG_OFFSET + (4 * GPREG_SIZE))
+#define PROBE_CPU_X5_OFFSET (PROBE_FIRST_GPREG_OFFSET + (5 * GPREG_SIZE))
+#define PROBE_CPU_X6_OFFSET (PROBE_FIRST_GPREG_OFFSET + (6 * GPREG_SIZE))
+#define PROBE_CPU_X7_OFFSET (PROBE_FIRST_GPREG_OFFSET + (7 * GPREG_SIZE))
+#define PROBE_CPU_X8_OFFSET (PROBE_FIRST_GPREG_OFFSET + (8 * GPREG_SIZE))
+#define PROBE_CPU_X9_OFFSET (PROBE_FIRST_GPREG_OFFSET + (9 * GPREG_SIZE))
+#define PROBE_CPU_X10_OFFSET (PROBE_FIRST_GPREG_OFFSET + (10 * GPREG_SIZE))
+#define PROBE_CPU_X11_OFFSET (PROBE_FIRST_GPREG_OFFSET + (11 * GPREG_SIZE))
+#define PROBE_CPU_X12_OFFSET (PROBE_FIRST_GPREG_OFFSET + (12 * GPREG_SIZE))
+#define PROBE_CPU_X13_OFFSET (PROBE_FIRST_GPREG_OFFSET + (13 * GPREG_SIZE))
+#define PROBE_CPU_X14_OFFSET (PROBE_FIRST_GPREG_OFFSET + (14 * GPREG_SIZE))
+#define PROBE_CPU_X15_OFFSET (PROBE_FIRST_GPREG_OFFSET + (15 * GPREG_SIZE))
+#define PROBE_CPU_X16_OFFSET (PROBE_FIRST_GPREG_OFFSET + (16 * GPREG_SIZE))
+#define PROBE_CPU_X17_OFFSET (PROBE_FIRST_GPREG_OFFSET + (17 * GPREG_SIZE))
+#define PROBE_CPU_X18_OFFSET (PROBE_FIRST_GPREG_OFFSET + (18 * GPREG_SIZE))
+#define PROBE_CPU_X19_OFFSET (PROBE_FIRST_GPREG_OFFSET + (19 * GPREG_SIZE))
+#define PROBE_CPU_X20_OFFSET (PROBE_FIRST_GPREG_OFFSET + (20 * GPREG_SIZE))
+#define PROBE_CPU_X21_OFFSET (PROBE_FIRST_GPREG_OFFSET + (21 * GPREG_SIZE))
+#define PROBE_CPU_X22_OFFSET (PROBE_FIRST_GPREG_OFFSET + (22 * GPREG_SIZE))
+#define PROBE_CPU_X23_OFFSET (PROBE_FIRST_GPREG_OFFSET + (23 * GPREG_SIZE))
+#define PROBE_CPU_X24_OFFSET (PROBE_FIRST_GPREG_OFFSET + (24 * GPREG_SIZE))
+#define PROBE_CPU_X25_OFFSET (PROBE_FIRST_GPREG_OFFSET + (25 * GPREG_SIZE))
+#define PROBE_CPU_X26_OFFSET (PROBE_FIRST_GPREG_OFFSET + (26 * GPREG_SIZE))
+#define PROBE_CPU_X27_OFFSET (PROBE_FIRST_GPREG_OFFSET + (27 * GPREG_SIZE))
+#define PROBE_CPU_X28_OFFSET (PROBE_FIRST_GPREG_OFFSET + (28 * GPREG_SIZE))
+#define PROBE_CPU_FP_OFFSET (PROBE_FIRST_GPREG_OFFSET + (29 * GPREG_SIZE))
+#define PROBE_CPU_LR_OFFSET (PROBE_FIRST_GPREG_OFFSET + (30 * GPREG_SIZE))
+#define PROBE_CPU_SP_OFFSET (PROBE_FIRST_GPREG_OFFSET + (31 * GPREG_SIZE))
+
+#define PROBE_CPU_PC_OFFSET (PROBE_FIRST_GPREG_OFFSET + (32 * GPREG_SIZE))
+#define PROBE_CPU_NZCV_OFFSET (PROBE_FIRST_GPREG_OFFSET + (33 * GPREG_SIZE))
+#define PROBE_CPU_FPSR_OFFSET (PROBE_FIRST_GPREG_OFFSET + (34 * GPREG_SIZE))
+
+#define PROBE_FIRST_FPREG_OFFSET (PROBE_FIRST_GPREG_OFFSET + (35 * GPREG_SIZE))
+
+#define FPREG_SIZE 8
+#define PROBE_CPU_Q0_OFFSET (PROBE_FIRST_FPREG_OFFSET + (0 * FPREG_SIZE))
+#define PROBE_CPU_Q1_OFFSET (PROBE_FIRST_FPREG_OFFSET + (1 * FPREG_SIZE))
+#define PROBE_CPU_Q2_OFFSET (PROBE_FIRST_FPREG_OFFSET + (2 * FPREG_SIZE))
+#define PROBE_CPU_Q3_OFFSET (PROBE_FIRST_FPREG_OFFSET + (3 * FPREG_SIZE))
+#define PROBE_CPU_Q4_OFFSET (PROBE_FIRST_FPREG_OFFSET + (4 * FPREG_SIZE))
+#define PROBE_CPU_Q5_OFFSET (PROBE_FIRST_FPREG_OFFSET + (5 * FPREG_SIZE))
+#define PROBE_CPU_Q6_OFFSET (PROBE_FIRST_FPREG_OFFSET + (6 * FPREG_SIZE))
+#define PROBE_CPU_Q7_OFFSET (PROBE_FIRST_FPREG_OFFSET + (7 * FPREG_SIZE))
+#define PROBE_CPU_Q8_OFFSET (PROBE_FIRST_FPREG_OFFSET + (8 * FPREG_SIZE))
+#define PROBE_CPU_Q9_OFFSET (PROBE_FIRST_FPREG_OFFSET + (9 * FPREG_SIZE))
+#define PROBE_CPU_Q10_OFFSET (PROBE_FIRST_FPREG_OFFSET + (10 * FPREG_SIZE))
+#define PROBE_CPU_Q11_OFFSET (PROBE_FIRST_FPREG_OFFSET + (11 * FPREG_SIZE))
+#define PROBE_CPU_Q12_OFFSET (PROBE_FIRST_FPREG_OFFSET + (12 * FPREG_SIZE))
+#define PROBE_CPU_Q13_OFFSET (PROBE_FIRST_FPREG_OFFSET + (13 * FPREG_SIZE))
+#define PROBE_CPU_Q14_OFFSET (PROBE_FIRST_FPREG_OFFSET + (14 * FPREG_SIZE))
+#define PROBE_CPU_Q15_OFFSET (PROBE_FIRST_FPREG_OFFSET + (15 * FPREG_SIZE))
+#define PROBE_CPU_Q16_OFFSET (PROBE_FIRST_FPREG_OFFSET + (16 * FPREG_SIZE))
+#define PROBE_CPU_Q17_OFFSET (PROBE_FIRST_FPREG_OFFSET + (17 * FPREG_SIZE))
+#define PROBE_CPU_Q18_OFFSET (PROBE_FIRST_FPREG_OFFSET + (18 * FPREG_SIZE))
+#define PROBE_CPU_Q19_OFFSET (PROBE_FIRST_FPREG_OFFSET + (19 * FPREG_SIZE))
+#define PROBE_CPU_Q20_OFFSET (PROBE_FIRST_FPREG_OFFSET + (20 * FPREG_SIZE))
+#define PROBE_CPU_Q21_OFFSET (PROBE_FIRST_FPREG_OFFSET + (21 * FPREG_SIZE))
+#define PROBE_CPU_Q22_OFFSET (PROBE_FIRST_FPREG_OFFSET + (22 * FPREG_SIZE))
+#define PROBE_CPU_Q23_OFFSET (PROBE_FIRST_FPREG_OFFSET + (23 * FPREG_SIZE))
+#define PROBE_CPU_Q24_OFFSET (PROBE_FIRST_FPREG_OFFSET + (24 * FPREG_SIZE))
+#define PROBE_CPU_Q25_OFFSET (PROBE_FIRST_FPREG_OFFSET + (25 * FPREG_SIZE))
+#define PROBE_CPU_Q26_OFFSET (PROBE_FIRST_FPREG_OFFSET + (26 * FPREG_SIZE))
+#define PROBE_CPU_Q27_OFFSET (PROBE_FIRST_FPREG_OFFSET + (27 * FPREG_SIZE))
+#define PROBE_CPU_Q28_OFFSET (PROBE_FIRST_FPREG_OFFSET + (28 * FPREG_SIZE))
+#define PROBE_CPU_Q29_OFFSET (PROBE_FIRST_FPREG_OFFSET + (29 * FPREG_SIZE))
+#define PROBE_CPU_Q30_OFFSET (PROBE_FIRST_FPREG_OFFSET + (30 * FPREG_SIZE))
+#define PROBE_CPU_Q31_OFFSET (PROBE_FIRST_FPREG_OFFSET + (31 * FPREG_SIZE))
+#define PROBE_SIZE (PROBE_FIRST_FPREG_OFFSET + (32 * FPREG_SIZE))
+#define SAVED_CALLER_SP PROBE_SIZE
+#define PROBE_SIZE_PLUS_SAVED_CALLER_SP (SAVED_CALLER_SP + PTR_SIZE)
+
+// These ASSERTs remind you that if you change the layout of ProbeContext,
+// you need to change ctiMasmProbeTrampoline offsets above to match.
+#define PROBE_OFFSETOF(x) offsetof(struct MacroAssembler::ProbeContext, x)
+COMPILE_ASSERT(PROBE_OFFSETOF(probeFunction) == PROBE_PROBE_FUNCTION_OFFSET, ProbeContext_probeFunction_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(arg1) == PROBE_ARG1_OFFSET, ProbeContext_arg1_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(arg2) == PROBE_ARG2_OFFSET, ProbeContext_arg2_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x0) == PROBE_CPU_X0_OFFSET, ProbeContext_cpu_x0_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x1) == PROBE_CPU_X1_OFFSET, ProbeContext_cpu_x1_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x2) == PROBE_CPU_X2_OFFSET, ProbeContext_cpu_x2_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x3) == PROBE_CPU_X3_OFFSET, ProbeContext_cpu_x3_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x4) == PROBE_CPU_X4_OFFSET, ProbeContext_cpu_x4_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x5) == PROBE_CPU_X5_OFFSET, ProbeContext_cpu_x5_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x6) == PROBE_CPU_X6_OFFSET, ProbeContext_cpu_x6_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x7) == PROBE_CPU_X7_OFFSET, ProbeContext_cpu_x7_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x8) == PROBE_CPU_X8_OFFSET, ProbeContext_cpu_x8_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x9) == PROBE_CPU_X9_OFFSET, ProbeContext_cpu_x9_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x10) == PROBE_CPU_X10_OFFSET, ProbeContext_cpu_x10_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x11) == PROBE_CPU_X11_OFFSET, ProbeContext_cpu_x11_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x12) == PROBE_CPU_X12_OFFSET, ProbeContext_cpu_x12_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x13) == PROBE_CPU_X13_OFFSET, ProbeContext_cpu_x13_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x14) == PROBE_CPU_X14_OFFSET, ProbeContext_cpu_x14_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x15) == PROBE_CPU_X15_OFFSET, ProbeContext_cpu_x15_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x16) == PROBE_CPU_X16_OFFSET, ProbeContext_cpu_x16_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x17) == PROBE_CPU_X17_OFFSET, ProbeContext_cpu_x17_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x18) == PROBE_CPU_X18_OFFSET, ProbeContext_cpu_x18_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x19) == PROBE_CPU_X19_OFFSET, ProbeContext_cpu_x19_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x20) == PROBE_CPU_X20_OFFSET, ProbeContext_cpu_x20_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x21) == PROBE_CPU_X21_OFFSET, ProbeContext_cpu_x21_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x22) == PROBE_CPU_X22_OFFSET, ProbeContext_cpu_x22_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x23) == PROBE_CPU_X23_OFFSET, ProbeContext_cpu_x23_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x24) == PROBE_CPU_X24_OFFSET, ProbeContext_cpu_x24_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x25) == PROBE_CPU_X25_OFFSET, ProbeContext_cpu_x25_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x26) == PROBE_CPU_X26_OFFSET, ProbeContext_cpu_x26_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x27) == PROBE_CPU_X27_OFFSET, ProbeContext_cpu_x27_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.x28) == PROBE_CPU_X28_OFFSET, ProbeContext_cpu_x28_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.fp) == PROBE_CPU_FP_OFFSET, ProbeContext_cpu_fp_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.lr) == PROBE_CPU_LR_OFFSET, ProbeContext_cpu_lr_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.sp) == PROBE_CPU_SP_OFFSET, ProbeContext_cpu_sp_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.pc) == PROBE_CPU_PC_OFFSET, ProbeContext_cpu_pc_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.nzcv) == PROBE_CPU_NZCV_OFFSET, ProbeContext_cpu_nzcv_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.fpsr) == PROBE_CPU_FPSR_OFFSET, ProbeContext_cpu_fpsr_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q0) == PROBE_CPU_Q0_OFFSET, ProbeContext_cpu_q0_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q1) == PROBE_CPU_Q1_OFFSET, ProbeContext_cpu_q1_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q2) == PROBE_CPU_Q2_OFFSET, ProbeContext_cpu_q2_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q3) == PROBE_CPU_Q3_OFFSET, ProbeContext_cpu_q3_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q4) == PROBE_CPU_Q4_OFFSET, ProbeContext_cpu_q4_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q5) == PROBE_CPU_Q5_OFFSET, ProbeContext_cpu_q5_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q6) == PROBE_CPU_Q6_OFFSET, ProbeContext_cpu_q6_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q7) == PROBE_CPU_Q7_OFFSET, ProbeContext_cpu_q7_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q8) == PROBE_CPU_Q8_OFFSET, ProbeContext_cpu_q8_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q9) == PROBE_CPU_Q9_OFFSET, ProbeContext_cpu_q9_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q10) == PROBE_CPU_Q10_OFFSET, ProbeContext_cpu_q10_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q11) == PROBE_CPU_Q11_OFFSET, ProbeContext_cpu_q11_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q12) == PROBE_CPU_Q12_OFFSET, ProbeContext_cpu_q12_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q13) == PROBE_CPU_Q13_OFFSET, ProbeContext_cpu_q13_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q14) == PROBE_CPU_Q14_OFFSET, ProbeContext_cpu_q14_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q15) == PROBE_CPU_Q15_OFFSET, ProbeContext_cpu_q15_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q16) == PROBE_CPU_Q16_OFFSET, ProbeContext_cpu_q16_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q17) == PROBE_CPU_Q17_OFFSET, ProbeContext_cpu_q17_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q18) == PROBE_CPU_Q18_OFFSET, ProbeContext_cpu_q18_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q19) == PROBE_CPU_Q19_OFFSET, ProbeContext_cpu_q19_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q20) == PROBE_CPU_Q20_OFFSET, ProbeContext_cpu_q20_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q21) == PROBE_CPU_Q21_OFFSET, ProbeContext_cpu_q21_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q22) == PROBE_CPU_Q22_OFFSET, ProbeContext_cpu_q22_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q23) == PROBE_CPU_Q23_OFFSET, ProbeContext_cpu_q23_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q24) == PROBE_CPU_Q24_OFFSET, ProbeContext_cpu_q24_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q25) == PROBE_CPU_Q25_OFFSET, ProbeContext_cpu_q25_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q26) == PROBE_CPU_Q26_OFFSET, ProbeContext_cpu_q26_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q27) == PROBE_CPU_Q27_OFFSET, ProbeContext_cpu_q27_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q28) == PROBE_CPU_Q28_OFFSET, ProbeContext_cpu_q28_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q29) == PROBE_CPU_Q29_OFFSET, ProbeContext_cpu_q29_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q30) == PROBE_CPU_Q30_OFFSET, ProbeContext_cpu_q30_offset_matches_ctiMasmProbeTrampoline);
+COMPILE_ASSERT(PROBE_OFFSETOF(cpu.q31) == PROBE_CPU_Q31_OFFSET, ProbeContext_cpu_q31_offset_matches_ctiMasmProbeTrampoline);
+
+COMPILE_ASSERT(sizeof(MacroAssembler::ProbeContext) == PROBE_SIZE, ProbeContext_size_matches_ctiMasmProbeTrampoline);
+
+#undef PROBE_OFFSETOF
+
+asm (
+&quot;.text&quot; &quot;\n&quot;
+&quot;.align 2&quot; &quot;\n&quot;
+&quot;.globl &quot; SYMBOL_STRING(ctiMasmProbeTrampoline) &quot;\n&quot;
+HIDE_SYMBOL(ctiMasmProbeTrampoline) &quot;\n&quot;
+SYMBOL_STRING(ctiMasmProbeTrampoline) &quot;:&quot; &quot;\n&quot;
+
+    // MacroAssembler::probe() has already generated code to store some values.
+    // The top of stack (the caller save buffer) now looks like this:
+    //     sp[0 * ptrSize]: probeFunction
+    //     sp[1 * ptrSize]: arg1
+    //     sp[2 * ptrSize]: arg2
+    //     sp[3 * ptrSize]: address of arm64ProbeTrampoline()
+    //     sp[4 * ptrSize]: saved x27
+    //     sp[5 * ptrSize]: saved x28
+    //     sp[6 * ptrSize]: saved lr
+    //     sp[7 * ptrSize]: saved sp
+
+    &quot;mov       x27, sp&quot; &quot;\n&quot;
+    &quot;mov       x28, sp&quot; &quot;\n&quot;
+
+    &quot;sub       x28, x28, #&quot; STRINGIZE_VALUE_OF(PROBE_SIZE_PLUS_SAVED_CALLER_SP) &quot;\n&quot;
+
+    // The ARM EABI specifies that the stack needs to be 16 byte aligned.
+    &quot;bic       x28, x28, #0xf&quot; &quot;\n&quot;
+    &quot;mov       sp, x28&quot; &quot;\n&quot;
+
+    &quot;str       x27, [sp, #&quot; STRINGIZE_VALUE_OF(SAVED_CALLER_SP) &quot;]&quot; &quot;\n&quot;
+
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X0_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x1, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X1_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x2, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X2_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x3, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X3_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x4, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X4_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x5, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X5_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x6, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X6_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x7, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X7_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x8, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X8_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x9, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X9_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x10, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X10_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x11, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X11_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x12, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X12_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x13, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X13_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x14, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X14_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x15, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X15_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x16, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X16_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x17, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X17_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x18, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X18_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x19, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X19_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x20, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X20_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x21, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X21_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x22, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X22_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x23, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X23_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x24, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X24_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x25, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X25_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x26, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X26_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x0, [x27, #4 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X27_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x0, [x27, #5 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X28_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;str       fp, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_FP_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x0, [x27, #6 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_LR_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x0, [x27, #7 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_SP_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;str       lr, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_PC_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;mrs       x0, nzcv&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_NZCV_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;mrs       x0, fpsr&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_FPSR_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x0, [x27, #0 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_PROBE_FUNCTION_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x0, [x27, #1 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_ARG1_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x0, [x27, #2 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_ARG2_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;str       d0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q0_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d1, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q1_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d2, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q2_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d3, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q3_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d4, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q4_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d5, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q5_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d6, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q6_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d7, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q7_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d8, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q8_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d9, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q9_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d10, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q10_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d11, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q11_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d12, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q12_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d13, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q13_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d14, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q14_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d15, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q15_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d16, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q16_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d17, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q17_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d18, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q18_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d19, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q19_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d20, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q20_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d21, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q21_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d22, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q22_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d23, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q23_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d24, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q24_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d25, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q25_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d26, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q26_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q27_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d28, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q28_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d29, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q29_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d30, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q30_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       d31, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q31_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;mov       x28, sp&quot; &quot;\n&quot; // Save the ProbeContext*.
+
+    &quot;mov       x0, sp&quot; &quot;\n&quot; // the ProbeContext* arg.
+    &quot;ldr       x27, [x27, #3 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+    &quot;blr       x27&quot; &quot;\n&quot;
+
+    &quot;mov       sp, x28&quot; &quot;\n&quot;
+
+    // To enable probes to modify register state, we copy all registers
+    // out of the ProbeContext before returning. That is except for x18, pc and sp.
+
+    // x18 is &quot;reserved for the platform. Conforming software should not make use of it.&quot;
+    // Hence, the JITs would not be using it, and the probe should also not be modifying it.
+    // See https://developer.apple.com/library/ios/documentation/Xcode/Conceptual/iPhoneOSABIReference/Articles/ARM64FunctionCallingConventions.html.
+
+    // We can't modify the pc, because the only way to set its value on ARM64 is via
+    // an indirect branch or a ret, which means we'll need a free register to do so.
+    // The probe mechanism is required to not perturb any registers that the caller
+    // may use. Hence, we don't have this free register available.
+
+    // In order to return to the caller, we need to ret via lr. The probe mechanism will
+    // restore lr's value after returning to the caller by loading the restore value
+    // from the caller save buffer. The caller expects to access the caller save buffer via
+    // sp. Hence, we cannot allow sp to be modified by the probe.
+
+    &quot;ldr       d0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q0_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d1, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q1_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d2, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q2_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d3, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q3_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d4, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q4_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d5, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q5_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d6, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q6_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d7, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q7_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d8, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q8_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d9, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q9_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d10, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q10_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d11, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q11_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d12, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q12_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d13, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q13_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d14, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q14_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d15, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q15_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d16, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q16_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d17, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q17_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d18, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q18_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d19, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q19_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d20, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q20_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d21, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q21_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d22, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q22_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d23, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q23_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d24, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q24_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d25, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q25_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d26, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q26_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q27_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d28, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q28_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d29, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q29_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d30, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q30_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       d31, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_Q31_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x0, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X0_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x1, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X1_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x2, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X2_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x3, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X3_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x4, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X4_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x5, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X5_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x6, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X6_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x7, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X7_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x8, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X8_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x9, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X9_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x10, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X10_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x11, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X11_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x12, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X12_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x13, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X13_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x14, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X14_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x15, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X15_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x16, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X16_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x17, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X17_OFFSET) &quot;]&quot; &quot;\n&quot;
+    // x18 should not be modified by the probe. See comment above for details.
+    &quot;ldr       x19, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X19_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x20, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X20_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x21, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X21_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x22, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X22_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x23, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X23_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x24, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X24_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x25, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X25_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x26, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X26_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_FPSR_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;msr       fpsr, x27&quot; &quot;\n&quot;
+
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_NZCV_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;msr       nzcv, x27&quot; &quot;\n&quot;
+    &quot;ldr       fp, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_FP_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X27_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x28, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X28_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    // There are 4 more registers left to restore: x27, x28, lr, sp, and pc.
+    // The JIT code's lr and sp will be restored by the caller.
+
+    // Restore pc by loading it into lr. The ret below will put in the pc.
+    &quot;ldr       lr, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_PC_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    // We need x27 as a scratch register to help with popping the ProbeContext.
+    // Hence, before we pop the ProbeContext, we need to copy the restore value
+    // for x27 from the ProbeContext to the caller save buffer.
+    &quot;ldr       x28, [sp, #&quot; STRINGIZE_VALUE_OF(SAVED_CALLER_SP) &quot;]&quot; &quot;\n&quot;
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X27_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x27, [x28, #4 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+
+    // Since lr is also restored by the caller, we need to copy its restore
+    // value to the caller save buffer too.
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_LR_OFFSET) &quot;]&quot; &quot;\n&quot;
+    &quot;str       x27, [x28, #6 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+
+    // We're now done with x28, and can restore its value.
+    &quot;ldr       x28, [sp, #&quot; STRINGIZE_VALUE_OF(PROBE_CPU_X28_OFFSET) &quot;]&quot; &quot;\n&quot;
+
+    // We're now done with the ProbeContext, and can pop it to restore sp so that
+    // it points to the caller save buffer.
+    &quot;ldr       x27, [sp, #&quot; STRINGIZE_VALUE_OF(SAVED_CALLER_SP) &quot;]&quot; &quot;\n&quot;
+    &quot;mov       sp, x27&quot; &quot;\n&quot;
+
+     // We're now done with x27, and can restore it.
+    &quot;ldr       x27, [sp, #4 * &quot; STRINGIZE_VALUE_OF(PTR_SIZE) &quot;]&quot; &quot;\n&quot;
+
+    &quot;ret&quot; &quot;\n&quot;
+);
+#endif // ENABLE(MASM_PROBE)
+
+#endif // COMPILER(GCC_OR_CLANG)
+
+} // namespace JSC
+
+#endif // JITStubsARM64_h
</ins></span></pre>
</div>
</div>

</body>
</html>