]> git.saurik.com Git - apple/javascriptcore.git/blobdiff - disassembler/ARM64/A64DOpcode.cpp
JavaScriptCore-7600.1.4.13.1.tar.gz
[apple/javascriptcore.git] / disassembler / ARM64 / A64DOpcode.cpp
index 5e79cc3f77c94c51b79de6549c850aae2048575e..415dbdb8e02ded4e318c82715df6542f5b1342ac 100644 (file)
@@ -24,8 +24,8 @@
  */
 
 #include "config.h"
-
 #include "A64DOpcode.h"
+
 #include <stdarg.h>
 #include <stdint.h>
 #include <stdio.h>
@@ -35,12 +35,13 @@ namespace JSC { namespace ARM64Disassembler {
 A64DOpcode::OpcodeGroup* A64DOpcode::opcodeTable[32];
 
 const char* const A64DOpcode::s_conditionNames[16] = {
-   "eq", "ne", "hs", "lo", "mi", "pl", "vs", "vc",
-   "hi", "ls", "ge", "lt", "gt", "le", "al", "ne"
+    "eq", "ne", "hs", "lo", "mi", "pl", "vs", "vc",
+    "hi", "ls", "ge", "lt", "gt", "le", "al", "ne"
 };
 
-const char* const A64DOpcode::s_optionName[8] =
-{ "uxtb", "uxth", "uxtw", "uxtx", "sxtb", "sxth", "sxtw", "sxtx" };
+const char* const A64DOpcode::s_optionName[8] = {
+    "uxtb", "uxth", "uxtw", "uxtx", "sxtb", "sxth", "sxtw", "sxtx"
+};
 
 const char* const A64DOpcode::s_shiftNames[4] = {
     "lsl", "lsr", "asl", "ror"
@@ -61,6 +62,8 @@ struct OpcodeGroupInitializer {
 { groupIndex, groupClass::mask, groupClass::pattern, groupClass::format }
 
 static OpcodeGroupInitializer opcodeGroupList[] = {
+    OPCODE_GROUP_ENTRY(0x08, A64DOpcodeLoadStoreRegisterPair),
+    OPCODE_GROUP_ENTRY(0x09, A64DOpcodeLoadStoreRegisterPair),
     OPCODE_GROUP_ENTRY(0x0a, A64DOpcodeLogicalShiftedRegister),
     OPCODE_GROUP_ENTRY(0x0b, A64DOpcodeAddSubtractExtendedRegister),
     OPCODE_GROUP_ENTRY(0x0b, A64DOpcodeAddSubtractShiftedRegister),
@@ -171,6 +174,11 @@ const char* A64DOpcode::format()
 
 void A64DOpcode::appendRegisterName(unsigned registerNumber, bool is64Bit)
 {
+    if (registerNumber == 29) {
+        bufferPrintf(is64Bit ? "fp" : "wfp");
+        return;
+    }
+
     if (registerNumber == 30) {
         bufferPrintf(is64Bit ? "lr" : "wlr");
         return;
@@ -400,8 +408,7 @@ const char* A64DOpcodeConditionalSelect::format()
     if (op2() & 0x2)
         return A64DOpcode::format();
 
-    if (rn() == rm() && (opNum() == 1 || opNum() == 2))
-    {
+    if (rn() == rm() && (opNum() == 1 || opNum() == 2)) {
         if (rn() == 31) {
             appendInstructionName((opNum() == 1) ? "cset" : "csetm");
             appendRegisterName(rd(), is64Bit());
@@ -526,15 +533,15 @@ const char* A64OpcodeExceptionGeneration::format()
             break;
         case 0x5: // DPCS1-3
             switch (ll()) {
-                case 0x1:
-                    opname = "dpcs1";
-                    break;
-                case 0x2:
-                    opname = "dpcs2";
-                    break;
-                case 0x3:
-                    opname = "dpcs3";
-                    break;
+            case 0x1:
+                opname = "dpcs1";
+                break;
+            case 0x2:
+                opname = "dpcs2";
+                break;
+            case 0x3:
+                opname = "dpcs3";
+                break;
             }
             break;
         }
@@ -745,7 +752,7 @@ const char* A64DOpcodeFloatingPointIntegerConversions::format()
     if (type() == 0x3)
         return A64DOpcode::format();
 
-    if (((rmode() & 0x1) || (rmode() & 0x2)) && (((opcode() & 0x6) == 0x2)|| ((opcode() & 0x6) == 0x4)))
+    if (((rmode() & 0x1) || (rmode() & 0x2)) && (((opcode() & 0x6) == 0x2) || ((opcode() & 0x6) == 0x4)))
         return A64DOpcode::format();
 
     if ((type() == 0x2) && (!(opcode() & 0x4) || ((opcode() & 0x6) == 0x4)))
@@ -859,7 +866,7 @@ const char* A64DOpcodeLoadStoreImmediate::format()
     appendCharacter('[');
     appendSPOrRegisterName(rn());
 
-    switch(type()) {
+    switch (type()) {
     case 0: // Unscaled Immediate
         if (immediate9()) {
             appendSeparator();
@@ -939,6 +946,63 @@ const char* A64DOpcodeLoadStoreRegisterOffset::format()
     return m_formatBuffer;
 }
 
+const char* A64DOpcodeLoadStoreRegisterPair::opName()
+{
+    if (!vBit() && lBit() && size() == 0x1)
+        return "ldpsw";
+    if (lBit())
+        return "ldp";
+    return "stp";
+}
+
+const char* A64DOpcodeLoadStoreRegisterPair::format()
+{
+    const char* thisOpName = opName();
+    
+    if (size() == 0x3)
+        return A64DOpcode::format();
+
+    if ((offsetMode() < 0x1) || (offsetMode() > 0x3))
+        return A64DOpcode::format();
+
+    if ((offsetMode() == 0x1) && !vBit() && !lBit())
+        return A64DOpcode::format();
+
+    appendInstructionName(thisOpName);
+    unsigned offsetShift;
+    if (vBit()) {
+        appendFPRegisterName(rt(), size());
+        appendSeparator();
+        appendFPRegisterName(rt2(), size());
+        offsetShift = size() + 2;
+    } else {
+        appendRegisterName(rt(), is64Bit());
+        appendSeparator();
+        appendRegisterName(rt2(), is64Bit());
+        offsetShift = (size() >> 1) + 2;
+    }
+
+    appendSeparator();
+    appendCharacter('[');
+    appendSPOrRegisterName(rn());
+
+    int offset = immediate7() << offsetShift;
+
+    if (offsetMode() == 1) {
+        appendCharacter(']');
+        appendSeparator();
+        appendSignedImmediate(offset);
+    } else {
+        appendSeparator();
+        appendSignedImmediate(offset);
+        appendCharacter(']');
+        if (offsetMode() == 0x3)
+            appendCharacter('!');
+    }
+
+    return m_formatBuffer;
+}
+
 const char* A64DOpcodeLoadStoreUnsignedImmediate::format()
 {
     const char* thisOpName = opName();