Home | History | Annotate | Download | only in ARM
      1 //===-- EmulateInstructionARM.cpp -------------------------------*- C++ -*-===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 
     10 #include <stdlib.h>
     11 
     12 #include "EmulateInstructionARM.h"
     13 #include "EmulationStateARM.h"
     14 #include "lldb/Core/ArchSpec.h"
     15 #include "lldb/Core/Address.h"
     16 #include "lldb/Core/ConstString.h"
     17 #include "lldb/Core/PluginManager.h"
     18 #include "lldb/Core/Stream.h"
     19 #include "lldb/Interpreter/OptionValueArray.h"
     20 #include "lldb/Interpreter/OptionValueDictionary.h"
     21 #include "lldb/Symbol/UnwindPlan.h"
     22 
     23 #include "Plugins/Process/Utility/ARMDefines.h"
     24 #include "Plugins/Process/Utility/ARMUtils.h"
     25 #include "Utility/ARM_DWARF_Registers.h"
     26 
     27 #include "llvm/Support/MathExtras.h" // for SignExtend32 template function
     28                                      // and countTrailingZeros function
     29 
     30 using namespace lldb;
     31 using namespace lldb_private;
     32 
     33 // Convenient macro definitions.
     34 #define APSR_C Bit32(m_opcode_cpsr, CPSR_C_POS)
     35 #define APSR_V Bit32(m_opcode_cpsr, CPSR_V_POS)
     36 
     37 #define AlignPC(pc_val) (pc_val & 0xFFFFFFFC)
     38 
     39 //----------------------------------------------------------------------
     40 //
     41 // ITSession implementation
     42 //
     43 //----------------------------------------------------------------------
     44 
     45 // A8.6.50
     46 // Valid return values are {1, 2, 3, 4}, with 0 signifying an error condition.
     47 static uint32_t
     48 CountITSize (uint32_t ITMask) {
     49     // First count the trailing zeros of the IT mask.
     50     uint32_t TZ = llvm::countTrailingZeros(ITMask);
     51     if (TZ > 3)
     52     {
     53 #ifdef LLDB_CONFIGURATION_DEBUG
     54         printf("Encoding error: IT Mask '0000'\n");
     55 #endif
     56         return 0;
     57     }
     58     return (4 - TZ);
     59 }
     60 
     61 // Init ITState.  Note that at least one bit is always 1 in mask.
     62 bool ITSession::InitIT(uint32_t bits7_0)
     63 {
     64     ITCounter = CountITSize(Bits32(bits7_0, 3, 0));
     65     if (ITCounter == 0)
     66         return false;
     67 
     68     // A8.6.50 IT
     69     unsigned short FirstCond = Bits32(bits7_0, 7, 4);
     70     if (FirstCond == 0xF)
     71     {
     72 #ifdef LLDB_CONFIGURATION_DEBUG
     73         printf("Encoding error: IT FirstCond '1111'\n");
     74 #endif
     75         return false;
     76     }
     77     if (FirstCond == 0xE && ITCounter != 1)
     78     {
     79 #ifdef LLDB_CONFIGURATION_DEBUG
     80         printf("Encoding error: IT FirstCond '1110' && Mask != '1000'\n");
     81 #endif
     82         return false;
     83     }
     84 
     85     ITState = bits7_0;
     86     return true;
     87 }
     88 
     89 // Update ITState if necessary.
     90 void ITSession::ITAdvance()
     91 {
     92     //assert(ITCounter);
     93     --ITCounter;
     94     if (ITCounter == 0)
     95         ITState = 0;
     96     else
     97     {
     98         unsigned short NewITState4_0 = Bits32(ITState, 4, 0) << 1;
     99         SetBits32(ITState, 4, 0, NewITState4_0);
    100     }
    101 }
    102 
    103 // Return true if we're inside an IT Block.
    104 bool ITSession::InITBlock()
    105 {
    106     return ITCounter != 0;
    107 }
    108 
    109 // Return true if we're the last instruction inside an IT Block.
    110 bool ITSession::LastInITBlock()
    111 {
    112     return ITCounter == 1;
    113 }
    114 
    115 // Get condition bits for the current thumb instruction.
    116 uint32_t ITSession::GetCond()
    117 {
    118     if (InITBlock())
    119         return Bits32(ITState, 7, 4);
    120     else
    121         return COND_AL;
    122 }
    123 
    124 // ARM constants used during decoding
    125 #define REG_RD          0
    126 #define LDM_REGLIST     1
    127 #define SP_REG          13
    128 #define LR_REG          14
    129 #define PC_REG          15
    130 #define PC_REGLIST_BIT  0x8000
    131 
    132 #define ARMv4     (1u << 0)
    133 #define ARMv4T    (1u << 1)
    134 #define ARMv5T    (1u << 2)
    135 #define ARMv5TE   (1u << 3)
    136 #define ARMv5TEJ  (1u << 4)
    137 #define ARMv6     (1u << 5)
    138 #define ARMv6K    (1u << 6)
    139 #define ARMv6T2   (1u << 7)
    140 #define ARMv7     (1u << 8)
    141 #define ARMv7S    (1u << 9)
    142 #define ARMv8     (1u << 10)
    143 #define ARMvAll   (0xffffffffu)
    144 
    145 #define ARMV4T_ABOVE  (ARMv4T|ARMv5T|ARMv5TE|ARMv5TEJ|ARMv6|ARMv6K|ARMv6T2|ARMv7|ARMv7S|ARMv8)
    146 #define ARMV5_ABOVE   (ARMv5T|ARMv5TE|ARMv5TEJ|ARMv6|ARMv6K|ARMv6T2|ARMv7|ARMv7S|ARMv8)
    147 #define ARMV5TE_ABOVE (ARMv5TE|ARMv5TEJ|ARMv6|ARMv6K|ARMv6T2|ARMv7|ARMv7S|ARMv8)
    148 #define ARMV5J_ABOVE  (ARMv5TEJ|ARMv6|ARMv6K|ARMv6T2|ARMv7|ARMv7S|ARMv8)
    149 #define ARMV6_ABOVE   (ARMv6|ARMv6K|ARMv6T2|ARMv7|ARMv7S|ARMv8)
    150 #define ARMV6T2_ABOVE (ARMv6T2|ARMv7|ARMv7S|ARMv8)
    151 #define ARMV7_ABOVE   (ARMv7|ARMv7S|ARMv8)
    152 
    153 #define No_VFP  0
    154 #define VFPv1   (1u << 1)
    155 #define VFPv2   (1u << 2)
    156 #define VFPv3   (1u << 3)
    157 #define AdvancedSIMD (1u << 4)
    158 
    159 #define VFPv1_ABOVE (VFPv1 | VFPv2 | VFPv3 | AdvancedSIMD)
    160 #define VFPv2_ABOVE (VFPv2 | VFPv3 | AdvancedSIMD)
    161 #define VFPv2v3     (VFPv2 | VFPv3)
    162 
    163 //----------------------------------------------------------------------
    164 //
    165 // EmulateInstructionARM implementation
    166 //
    167 //----------------------------------------------------------------------
    168 
    169 void
    170 EmulateInstructionARM::Initialize ()
    171 {
    172     PluginManager::RegisterPlugin (GetPluginNameStatic (),
    173                                    GetPluginDescriptionStatic (),
    174                                    CreateInstance);
    175 }
    176 
    177 void
    178 EmulateInstructionARM::Terminate ()
    179 {
    180     PluginManager::UnregisterPlugin (CreateInstance);
    181 }
    182 
    183 ConstString
    184 EmulateInstructionARM::GetPluginNameStatic ()
    185 {
    186     static ConstString g_name("arm");
    187     return g_name;
    188 }
    189 
    190 const char *
    191 EmulateInstructionARM::GetPluginDescriptionStatic ()
    192 {
    193     return "Emulate instructions for the ARM architecture.";
    194 }
    195 
    196 EmulateInstruction *
    197 EmulateInstructionARM::CreateInstance (const ArchSpec &arch, InstructionType inst_type)
    198 {
    199     if (EmulateInstructionARM::SupportsEmulatingIntructionsOfTypeStatic(inst_type))
    200     {
    201         if (arch.GetTriple().getArch() == llvm::Triple::arm)
    202         {
    203             std::unique_ptr<EmulateInstructionARM> emulate_insn_ap (new EmulateInstructionARM (arch));
    204 
    205             if (emulate_insn_ap.get())
    206                 return emulate_insn_ap.release();
    207         }
    208         else if (arch.GetTriple().getArch() == llvm::Triple::thumb)
    209         {
    210             std::unique_ptr<EmulateInstructionARM> emulate_insn_ap (new EmulateInstructionARM (arch));
    211 
    212             if (emulate_insn_ap.get())
    213                 return emulate_insn_ap.release();
    214         }
    215     }
    216 
    217     return NULL;
    218 }
    219 
    220 bool
    221 EmulateInstructionARM::SetTargetTriple (const ArchSpec &arch)
    222 {
    223     if (arch.GetTriple().getArch () == llvm::Triple::arm)
    224         return true;
    225     else if (arch.GetTriple().getArch () == llvm::Triple::thumb)
    226         return true;
    227 
    228     return false;
    229 }
    230 
    231 // Write "bits (32) UNKNOWN" to memory address "address".  Helper function for many ARM instructions.
    232 bool
    233 EmulateInstructionARM::WriteBits32UnknownToMemory (addr_t address)
    234 {
    235     EmulateInstruction::Context context;
    236     context.type = EmulateInstruction::eContextWriteMemoryRandomBits;
    237     context.SetNoArgs ();
    238 
    239     uint32_t random_data = rand ();
    240     const uint32_t addr_byte_size = GetAddressByteSize();
    241 
    242     if (!MemAWrite (context, address, random_data, addr_byte_size))
    243         return false;
    244 
    245     return true;
    246 }
    247 
    248 // Write "bits (32) UNKNOWN" to register n.  Helper function for many ARM instructions.
    249 bool
    250 EmulateInstructionARM::WriteBits32Unknown (int n)
    251 {
    252     EmulateInstruction::Context context;
    253     context.type = EmulateInstruction::eContextWriteRegisterRandomBits;
    254     context.SetNoArgs ();
    255 
    256     bool success;
    257     uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
    258 
    259     if (!success)
    260         return false;
    261 
    262     if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, data))
    263         return false;
    264 
    265     return true;
    266 }
    267 
    268 bool
    269 EmulateInstructionARM::GetRegisterInfo (uint32_t reg_kind, uint32_t reg_num, RegisterInfo &reg_info)
    270 {
    271     if (reg_kind == eRegisterKindGeneric)
    272     {
    273         switch (reg_num)
    274         {
    275             case LLDB_REGNUM_GENERIC_PC:    reg_kind = eRegisterKindDWARF; reg_num = dwarf_pc; break;
    276             case LLDB_REGNUM_GENERIC_SP:    reg_kind = eRegisterKindDWARF; reg_num = dwarf_sp; break;
    277             case LLDB_REGNUM_GENERIC_FP:    reg_kind = eRegisterKindDWARF; reg_num = dwarf_r7; break;
    278             case LLDB_REGNUM_GENERIC_RA:    reg_kind = eRegisterKindDWARF; reg_num = dwarf_lr; break;
    279             case LLDB_REGNUM_GENERIC_FLAGS: reg_kind = eRegisterKindDWARF; reg_num = dwarf_cpsr; break;
    280             default: return false;
    281         }
    282     }
    283 
    284     if (reg_kind == eRegisterKindDWARF)
    285         return GetARMDWARFRegisterInfo(reg_num, reg_info);
    286     return false;
    287 }
    288 
    289 uint32_t
    290 EmulateInstructionARM::GetFramePointerRegisterNumber () const
    291 {
    292     if (m_opcode_mode == eModeThumb)
    293     {
    294         switch (m_arch.GetTriple().getOS())
    295         {
    296             case llvm::Triple::Darwin:
    297             case llvm::Triple::MacOSX:
    298             case llvm::Triple::IOS:
    299                 return 7;
    300             default:
    301                 break;
    302         }
    303     }
    304     return 11;
    305 }
    306 
    307 uint32_t
    308 EmulateInstructionARM::GetFramePointerDWARFRegisterNumber () const
    309 {
    310     if (m_opcode_mode == eModeThumb)
    311     {
    312         switch (m_arch.GetTriple().getOS())
    313         {
    314             case llvm::Triple::Darwin:
    315             case llvm::Triple::MacOSX:
    316             case llvm::Triple::IOS:
    317                 return dwarf_r7;
    318             default:
    319                 break;
    320         }
    321     }
    322     return dwarf_r11;
    323 }
    324 
    325 // Push Multiple Registers stores multiple registers to the stack, storing to
    326 // consecutive memory locations ending just below the address in SP, and updates
    327 // SP to point to the start of the stored data.
    328 bool
    329 EmulateInstructionARM::EmulatePUSH (const uint32_t opcode, const ARMEncoding encoding)
    330 {
    331 #if 0
    332     // ARM pseudo code...
    333     if (ConditionPassed())
    334     {
    335         EncodingSpecificOperations();
    336         NullCheckIfThumbEE(13);
    337         address = SP - 4*BitCount(registers);
    338 
    339         for (i = 0 to 14)
    340         {
    341             if (registers<i> == '1')
    342             {
    343                 if i == 13 && i != LowestSetBit(registers) // Only possible for encoding A1
    344                     MemA[address,4] = bits(32) UNKNOWN;
    345                 else
    346                     MemA[address,4] = R[i];
    347                 address = address + 4;
    348             }
    349         }
    350 
    351         if (registers<15> == '1') // Only possible for encoding A1 or A2
    352             MemA[address,4] = PCStoreValue();
    353 
    354         SP = SP - 4*BitCount(registers);
    355     }
    356 #endif
    357 
    358     bool conditional = false;
    359     bool success = false;
    360     if (ConditionPassed(opcode, &conditional))
    361     {
    362         const uint32_t addr_byte_size = GetAddressByteSize();
    363         const addr_t sp = ReadCoreReg (SP_REG, &success);
    364         if (!success)
    365             return false;
    366         uint32_t registers = 0;
    367         uint32_t Rt; // the source register
    368         switch (encoding) {
    369         case eEncodingT1:
    370             registers = Bits32(opcode, 7, 0);
    371             // The M bit represents LR.
    372             if (Bit32(opcode, 8))
    373                 registers |= (1u << 14);
    374             // if BitCount(registers) < 1 then UNPREDICTABLE;
    375             if (BitCount(registers) < 1)
    376                 return false;
    377             break;
    378         case eEncodingT2:
    379             // Ignore bits 15 & 13.
    380             registers = Bits32(opcode, 15, 0) & ~0xa000;
    381             // if BitCount(registers) < 2 then UNPREDICTABLE;
    382             if (BitCount(registers) < 2)
    383                 return false;
    384             break;
    385         case eEncodingT3:
    386             Rt = Bits32(opcode, 15, 12);
    387             // if BadReg(t) then UNPREDICTABLE;
    388             if (BadReg(Rt))
    389                 return false;
    390             registers = (1u << Rt);
    391             break;
    392         case eEncodingA1:
    393             registers = Bits32(opcode, 15, 0);
    394             // Instead of return false, let's handle the following case as well,
    395             // which amounts to pushing one reg onto the full descending stacks.
    396             // if BitCount(register_list) < 2 then SEE STMDB / STMFD;
    397             break;
    398         case eEncodingA2:
    399             Rt = Bits32(opcode, 15, 12);
    400             // if t == 13 then UNPREDICTABLE;
    401             if (Rt == dwarf_sp)
    402                 return false;
    403             registers = (1u << Rt);
    404             break;
    405         default:
    406             return false;
    407         }
    408         addr_t sp_offset = addr_byte_size * BitCount (registers);
    409         addr_t addr = sp - sp_offset;
    410         uint32_t i;
    411 
    412         EmulateInstruction::Context context;
    413         if (conditional)
    414             context.type = EmulateInstruction::eContextRegisterStore;
    415         else
    416             context.type = EmulateInstruction::eContextPushRegisterOnStack;
    417         RegisterInfo reg_info;
    418         RegisterInfo sp_reg;
    419         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
    420         for (i=0; i<15; ++i)
    421         {
    422             if (BitIsSet (registers, i))
    423             {
    424                 GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + i, reg_info);
    425                 context.SetRegisterToRegisterPlusOffset (reg_info, sp_reg, addr - sp);
    426                 uint32_t reg_value = ReadCoreReg(i, &success);
    427                 if (!success)
    428                     return false;
    429                 if (!MemAWrite (context, addr, reg_value, addr_byte_size))
    430                     return false;
    431                 addr += addr_byte_size;
    432             }
    433         }
    434 
    435         if (BitIsSet (registers, 15))
    436         {
    437             GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, reg_info);
    438             context.SetRegisterToRegisterPlusOffset (reg_info, sp_reg, addr - sp);
    439             const uint32_t pc = ReadCoreReg(PC_REG, &success);
    440             if (!success)
    441                 return false;
    442             if (!MemAWrite (context, addr, pc, addr_byte_size))
    443                 return false;
    444         }
    445 
    446         context.type = EmulateInstruction::eContextAdjustStackPointer;
    447         context.SetImmediateSigned (-sp_offset);
    448 
    449         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, sp - sp_offset))
    450             return false;
    451     }
    452     return true;
    453 }
    454 
    455 // Pop Multiple Registers loads multiple registers from the stack, loading from
    456 // consecutive memory locations staring at the address in SP, and updates
    457 // SP to point just above the loaded data.
    458 bool
    459 EmulateInstructionARM::EmulatePOP (const uint32_t opcode, const ARMEncoding encoding)
    460 {
    461 #if 0
    462     // ARM pseudo code...
    463     if (ConditionPassed())
    464     {
    465         EncodingSpecificOperations(); NullCheckIfThumbEE(13);
    466         address = SP;
    467         for i = 0 to 14
    468             if registers<i> == '1' then
    469                 R[i] = if UnalignedAllowed then MemU[address,4] else MemA[address,4]; address = address + 4;
    470         if registers<15> == '1' then
    471             if UnalignedAllowed then
    472                 LoadWritePC(MemU[address,4]);
    473             else
    474                 LoadWritePC(MemA[address,4]);
    475         if registers<13> == '0' then SP = SP + 4*BitCount(registers);
    476         if registers<13> == '1' then SP = bits(32) UNKNOWN;
    477     }
    478 #endif
    479 
    480     bool success = false;
    481 
    482     bool conditional = false;
    483     if (ConditionPassed(opcode, &conditional))
    484     {
    485         const uint32_t addr_byte_size = GetAddressByteSize();
    486         const addr_t sp = ReadCoreReg (SP_REG, &success);
    487         if (!success)
    488             return false;
    489         uint32_t registers = 0;
    490         uint32_t Rt; // the destination register
    491         switch (encoding) {
    492         case eEncodingT1:
    493             registers = Bits32(opcode, 7, 0);
    494             // The P bit represents PC.
    495             if (Bit32(opcode, 8))
    496                 registers |= (1u << 15);
    497             // if BitCount(registers) < 1 then UNPREDICTABLE;
    498             if (BitCount(registers) < 1)
    499                 return false;
    500             break;
    501         case eEncodingT2:
    502             // Ignore bit 13.
    503             registers = Bits32(opcode, 15, 0) & ~0x2000;
    504             // if BitCount(registers) < 2 || (P == '1' && M == '1') then UNPREDICTABLE;
    505             if (BitCount(registers) < 2 || (Bit32(opcode, 15) && Bit32(opcode, 14)))
    506                 return false;
    507             // if registers<15> == '1' && InITBlock() && !LastInITBlock() then UNPREDICTABLE;
    508             if (BitIsSet(registers, 15) && InITBlock() && !LastInITBlock())
    509                 return false;
    510             break;
    511         case eEncodingT3:
    512             Rt = Bits32(opcode, 15, 12);
    513             // if t == 13 || (t == 15 && InITBlock() && !LastInITBlock()) then UNPREDICTABLE;
    514             if (Rt == 13)
    515                 return false;
    516             if (Rt == 15 && InITBlock() && !LastInITBlock())
    517                 return false;
    518             registers = (1u << Rt);
    519             break;
    520         case eEncodingA1:
    521             registers = Bits32(opcode, 15, 0);
    522             // Instead of return false, let's handle the following case as well,
    523             // which amounts to popping one reg from the full descending stacks.
    524             // if BitCount(register_list) < 2 then SEE LDM / LDMIA / LDMFD;
    525 
    526             // if registers<13> == '1' && ArchVersion() >= 7 then UNPREDICTABLE;
    527             if (BitIsSet(opcode, 13) && ArchVersion() >= ARMv7)
    528                 return false;
    529             break;
    530         case eEncodingA2:
    531             Rt = Bits32(opcode, 15, 12);
    532             // if t == 13 then UNPREDICTABLE;
    533             if (Rt == dwarf_sp)
    534                 return false;
    535             registers = (1u << Rt);
    536             break;
    537         default:
    538             return false;
    539         }
    540         addr_t sp_offset = addr_byte_size * BitCount (registers);
    541         addr_t addr = sp;
    542         uint32_t i, data;
    543 
    544         EmulateInstruction::Context context;
    545         if (conditional)
    546             context.type = EmulateInstruction::eContextRegisterLoad;
    547         else
    548             context.type = EmulateInstruction::eContextPopRegisterOffStack;
    549 
    550         RegisterInfo sp_reg;
    551         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
    552 
    553         for (i=0; i<15; ++i)
    554         {
    555             if (BitIsSet (registers, i))
    556             {
    557                 context.SetRegisterPlusOffset (sp_reg, addr - sp);
    558                 data = MemARead(context, addr, 4, 0, &success);
    559                 if (!success)
    560                     return false;
    561                 if (!WriteRegisterUnsigned(context, eRegisterKindDWARF, dwarf_r0 + i, data))
    562                     return false;
    563                 addr += addr_byte_size;
    564             }
    565         }
    566 
    567         if (BitIsSet (registers, 15))
    568         {
    569             context.SetRegisterPlusOffset (sp_reg, addr - sp);
    570             data = MemARead(context, addr, 4, 0, &success);
    571             if (!success)
    572                 return false;
    573             // In ARMv5T and above, this is an interworking branch.
    574             if (!LoadWritePC(context, data))
    575                 return false;
    576             //addr += addr_byte_size;
    577         }
    578 
    579         context.type = EmulateInstruction::eContextAdjustStackPointer;
    580         context.SetImmediateSigned (sp_offset);
    581 
    582         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, sp + sp_offset))
    583             return false;
    584     }
    585     return true;
    586 }
    587 
    588 // Set r7 or ip to point to saved value residing within the stack.
    589 // ADD (SP plus immediate)
    590 bool
    591 EmulateInstructionARM::EmulateADDRdSPImm (const uint32_t opcode, const ARMEncoding encoding)
    592 {
    593 #if 0
    594     // ARM pseudo code...
    595     if (ConditionPassed())
    596     {
    597         EncodingSpecificOperations();
    598         (result, carry, overflow) = AddWithCarry(SP, imm32, '0');
    599         if d == 15 then
    600            ALUWritePC(result); // setflags is always FALSE here
    601         else
    602             R[d] = result;
    603             if setflags then
    604                 APSR.N = result<31>;
    605                 APSR.Z = IsZeroBit(result);
    606                 APSR.C = carry;
    607                 APSR.V = overflow;
    608     }
    609 #endif
    610 
    611     bool success = false;
    612 
    613     if (ConditionPassed(opcode))
    614     {
    615         const addr_t sp = ReadCoreReg (SP_REG, &success);
    616         if (!success)
    617             return false;
    618         uint32_t Rd; // the destination register
    619         uint32_t imm32;
    620         switch (encoding) {
    621         case eEncodingT1:
    622             Rd = 7;
    623             imm32 = Bits32(opcode, 7, 0) << 2; // imm32 = ZeroExtend(imm8:'00', 32)
    624             break;
    625         case eEncodingA1:
    626             Rd = Bits32(opcode, 15, 12);
    627             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
    628             break;
    629         default:
    630             return false;
    631         }
    632         addr_t sp_offset = imm32;
    633         addr_t addr = sp + sp_offset; // a pointer to the stack area
    634 
    635         EmulateInstruction::Context context;
    636         context.type = eContextSetFramePointer;
    637         RegisterInfo sp_reg;
    638         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
    639         context.SetRegisterPlusOffset (sp_reg, sp_offset);
    640 
    641         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + Rd, addr))
    642             return false;
    643     }
    644     return true;
    645 }
    646 
    647 // Set r7 or ip to the current stack pointer.
    648 // MOV (register)
    649 bool
    650 EmulateInstructionARM::EmulateMOVRdSP (const uint32_t opcode, const ARMEncoding encoding)
    651 {
    652 #if 0
    653     // ARM pseudo code...
    654     if (ConditionPassed())
    655     {
    656         EncodingSpecificOperations();
    657         result = R[m];
    658         if d == 15 then
    659             ALUWritePC(result); // setflags is always FALSE here
    660         else
    661             R[d] = result;
    662             if setflags then
    663                 APSR.N = result<31>;
    664                 APSR.Z = IsZeroBit(result);
    665                 // APSR.C unchanged
    666                 // APSR.V unchanged
    667     }
    668 #endif
    669 
    670     bool success = false;
    671 
    672     if (ConditionPassed(opcode))
    673     {
    674         const addr_t sp = ReadCoreReg (SP_REG, &success);
    675         if (!success)
    676             return false;
    677         uint32_t Rd; // the destination register
    678         switch (encoding) {
    679         case eEncodingT1:
    680             Rd = 7;
    681             break;
    682         case eEncodingA1:
    683             Rd = 12;
    684             break;
    685         default:
    686             return false;
    687         }
    688 
    689         EmulateInstruction::Context context;
    690         if (Rd == GetFramePointerRegisterNumber())
    691             context.type = EmulateInstruction::eContextSetFramePointer;
    692         else
    693             context.type = EmulateInstruction::eContextRegisterPlusOffset;
    694         RegisterInfo sp_reg;
    695         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
    696         context.SetRegisterPlusOffset (sp_reg, 0);
    697 
    698         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + Rd, sp))
    699             return false;
    700     }
    701     return true;
    702 }
    703 
    704 // Move from high register (r8-r15) to low register (r0-r7).
    705 // MOV (register)
    706 bool
    707 EmulateInstructionARM::EmulateMOVLowHigh (const uint32_t opcode, const ARMEncoding encoding)
    708 {
    709     return EmulateMOVRdRm (opcode, encoding);
    710 }
    711 
    712 // Move from register to register.
    713 // MOV (register)
    714 bool
    715 EmulateInstructionARM::EmulateMOVRdRm (const uint32_t opcode, const ARMEncoding encoding)
    716 {
    717 #if 0
    718     // ARM pseudo code...
    719     if (ConditionPassed())
    720     {
    721         EncodingSpecificOperations();
    722         result = R[m];
    723         if d == 15 then
    724             ALUWritePC(result); // setflags is always FALSE here
    725         else
    726             R[d] = result;
    727             if setflags then
    728                 APSR.N = result<31>;
    729                 APSR.Z = IsZeroBit(result);
    730                 // APSR.C unchanged
    731                 // APSR.V unchanged
    732     }
    733 #endif
    734 
    735     bool success = false;
    736 
    737     if (ConditionPassed(opcode))
    738     {
    739         uint32_t Rm; // the source register
    740         uint32_t Rd; // the destination register
    741         bool setflags;
    742         switch (encoding) {
    743         case eEncodingT1:
    744             Rd = Bit32(opcode, 7) << 3 | Bits32(opcode, 2, 0);
    745             Rm = Bits32(opcode, 6, 3);
    746             setflags = false;
    747             if (Rd == 15 && InITBlock() && !LastInITBlock())
    748                 return false;
    749             break;
    750         case eEncodingT2:
    751             Rd = Bits32(opcode, 2, 0);
    752             Rm = Bits32(opcode, 5, 3);
    753             setflags = true;
    754             if (InITBlock())
    755                 return false;
    756             break;
    757         case eEncodingT3:
    758             Rd = Bits32(opcode, 11, 8);
    759             Rm = Bits32(opcode, 3, 0);
    760             setflags = BitIsSet(opcode, 20);
    761             // if setflags && (BadReg(d) || BadReg(m)) then UNPREDICTABLE;
    762             if (setflags && (BadReg(Rd) || BadReg(Rm)))
    763                 return false;
    764             // if !setflags && (d == 15 || m == 15 || (d == 13 && m == 13)) then UNPREDICTABLE;
    765             if (!setflags && (Rd == 15 || Rm == 15 || (Rd == 13 && Rm == 13)))
    766                 return false;
    767             break;
    768         case eEncodingA1:
    769             Rd = Bits32(opcode, 15, 12);
    770             Rm = Bits32(opcode, 3, 0);
    771             setflags = BitIsSet(opcode, 20);
    772 
    773             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
    774             if (Rd == 15 && setflags)
    775                 return EmulateSUBSPcLrEtc (opcode, encoding);
    776             break;
    777         default:
    778             return false;
    779         }
    780         uint32_t result = ReadCoreReg(Rm, &success);
    781         if (!success)
    782             return false;
    783 
    784         // The context specifies that Rm is to be moved into Rd.
    785         EmulateInstruction::Context context;
    786         context.type = EmulateInstruction::eContextRegisterLoad;
    787         RegisterInfo dwarf_reg;
    788         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, dwarf_reg);
    789         context.SetRegister (dwarf_reg);
    790 
    791         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags))
    792             return false;
    793     }
    794     return true;
    795 }
    796 
    797 // Move (immediate) writes an immediate value to the destination register.  It
    798 // can optionally update the condition flags based on the value.
    799 // MOV (immediate)
    800 bool
    801 EmulateInstructionARM::EmulateMOVRdImm (const uint32_t opcode, const ARMEncoding encoding)
    802 {
    803 #if 0
    804     // ARM pseudo code...
    805     if (ConditionPassed())
    806     {
    807         EncodingSpecificOperations();
    808         result = imm32;
    809         if d == 15 then         // Can only occur for ARM encoding
    810             ALUWritePC(result); // setflags is always FALSE here
    811         else
    812             R[d] = result;
    813             if setflags then
    814                 APSR.N = result<31>;
    815                 APSR.Z = IsZeroBit(result);
    816                 APSR.C = carry;
    817                 // APSR.V unchanged
    818     }
    819 #endif
    820 
    821     if (ConditionPassed(opcode))
    822     {
    823         uint32_t Rd; // the destination register
    824         uint32_t imm32; // the immediate value to be written to Rd
    825         uint32_t carry = 0; // the carry bit after ThumbExpandImm_C or ARMExpandImm_C.
    826                             // for setflags == false, this value is a don't care
    827                             // initialized to 0 to silence the static analyzer
    828         bool setflags;
    829         switch (encoding) {
    830             case eEncodingT1:
    831                 Rd = Bits32(opcode, 10, 8);
    832                 setflags = !InITBlock();
    833                 imm32 = Bits32(opcode, 7, 0); // imm32 = ZeroExtend(imm8, 32)
    834                 carry = APSR_C;
    835 
    836                 break;
    837 
    838             case eEncodingT2:
    839                 Rd = Bits32(opcode, 11, 8);
    840                 setflags = BitIsSet(opcode, 20);
    841                 imm32 = ThumbExpandImm_C(opcode, APSR_C, carry);
    842                 if (BadReg(Rd))
    843                   return false;
    844 
    845                 break;
    846 
    847             case eEncodingT3:
    848             {
    849                 // d = UInt(Rd); setflags = FALSE; imm32 = ZeroExtend(imm4:i:imm3:imm8, 32);
    850                 Rd = Bits32 (opcode, 11, 8);
    851                 setflags = false;
    852                 uint32_t imm4 = Bits32 (opcode, 19, 16);
    853                 uint32_t imm3 = Bits32 (opcode, 14, 12);
    854                 uint32_t i = Bit32 (opcode, 26);
    855                 uint32_t imm8 = Bits32 (opcode, 7, 0);
    856                 imm32 = (imm4 << 12) | (i << 11) | (imm3 << 8) | imm8;
    857 
    858                 // if BadReg(d) then UNPREDICTABLE;
    859                 if (BadReg (Rd))
    860                     return false;
    861             }
    862                 break;
    863 
    864             case eEncodingA1:
    865                 // d = UInt(Rd); setflags = (S == 1); (imm32, carry) = ARMExpandImm_C(imm12, APSR.C);
    866                 Rd = Bits32 (opcode, 15, 12);
    867                 setflags = BitIsSet (opcode, 20);
    868                 imm32 = ARMExpandImm_C (opcode, APSR_C, carry);
    869 
    870                 // if Rd == 1111 && S == 1 then SEE SUBS PC, LR and related instructions;
    871                 if ((Rd == 15) && setflags)
    872                     return EmulateSUBSPcLrEtc (opcode, encoding);
    873 
    874                 break;
    875 
    876             case eEncodingA2:
    877             {
    878                 // d = UInt(Rd); setflags = FALSE; imm32 = ZeroExtend(imm4:imm12, 32);
    879                 Rd = Bits32 (opcode, 15, 12);
    880                 setflags = false;
    881                 uint32_t imm4 = Bits32 (opcode, 19, 16);
    882                 uint32_t imm12 = Bits32 (opcode, 11, 0);
    883                 imm32 = (imm4 << 12) | imm12;
    884 
    885                 // if d == 15 then UNPREDICTABLE;
    886                 if (Rd == 15)
    887                     return false;
    888             }
    889                 break;
    890 
    891             default:
    892                 return false;
    893         }
    894         uint32_t result = imm32;
    895 
    896         // The context specifies that an immediate is to be moved into Rd.
    897         EmulateInstruction::Context context;
    898         context.type = EmulateInstruction::eContextImmediate;
    899         context.SetNoArgs ();
    900 
    901         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
    902             return false;
    903     }
    904     return true;
    905 }
    906 
    907 // MUL multiplies two register values.  The least significant 32 bits of the result are written to the destination
    908 // register.  These 32 bits do not depend on whether the source register values are considered to be signed values or
    909 // unsigned values.
    910 //
    911 // Optionally, it can update the condition flags based on the result.  In the Thumb instruction set, this option is
    912 // limited to only a few forms of the instruction.
    913 bool
    914 EmulateInstructionARM::EmulateMUL (const uint32_t opcode, const ARMEncoding encoding)
    915 {
    916 #if 0
    917     if ConditionPassed() then
    918         EncodingSpecificOperations();
    919         operand1 = SInt(R[n]); // operand1 = UInt(R[n]) produces the same final results
    920         operand2 = SInt(R[m]); // operand2 = UInt(R[m]) produces the same final results
    921         result = operand1 * operand2;
    922         R[d] = result<31:0>;
    923         if setflags then
    924             APSR.N = result<31>;
    925             APSR.Z = IsZeroBit(result);
    926             if ArchVersion() == 4 then
    927                 APSR.C = bit UNKNOWN;
    928             // else APSR.C unchanged
    929             // APSR.V always unchanged
    930 #endif
    931 
    932     if (ConditionPassed(opcode))
    933     {
    934         uint32_t d;
    935         uint32_t n;
    936         uint32_t m;
    937         bool setflags;
    938 
    939         // EncodingSpecificOperations();
    940         switch (encoding)
    941         {
    942             case eEncodingT1:
    943                 // d = UInt(Rdm); n = UInt(Rn); m = UInt(Rdm); setflags = !InITBlock();
    944                 d = Bits32 (opcode, 2, 0);
    945                 n = Bits32 (opcode, 5, 3);
    946                 m = Bits32 (opcode, 2, 0);
    947                 setflags = !InITBlock();
    948 
    949                 // if ArchVersion() < 6 && d == n then UNPREDICTABLE;
    950                 if ((ArchVersion() < ARMv6) && (d == n))
    951                     return false;
    952 
    953                 break;
    954 
    955             case eEncodingT2:
    956                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = FALSE;
    957                 d = Bits32 (opcode, 11, 8);
    958                 n = Bits32 (opcode, 19, 16);
    959                 m = Bits32 (opcode, 3, 0);
    960                 setflags = false;
    961 
    962                 // if BadReg(d) || BadReg(n) || BadReg(m) then UNPREDICTABLE;
    963                 if (BadReg (d) || BadReg (n) || BadReg (m))
    964                     return false;
    965 
    966                 break;
    967 
    968             case eEncodingA1:
    969                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = (S == '1');
    970                 d = Bits32 (opcode, 19, 16);
    971                 n = Bits32 (opcode, 3, 0);
    972                 m = Bits32 (opcode, 11, 8);
    973                 setflags = BitIsSet (opcode, 20);
    974 
    975                 // if d == 15 || n == 15 || m == 15 then UNPREDICTABLE;
    976                 if ((d == 15) ||  (n == 15) || (m == 15))
    977                     return false;
    978 
    979                 // if ArchVersion() < 6 && d == n then UNPREDICTABLE;
    980                 if ((ArchVersion() < ARMv6) && (d == n))
    981                     return false;
    982 
    983                 break;
    984 
    985             default:
    986                 return false;
    987         }
    988 
    989         bool success = false;
    990 
    991         // operand1 = SInt(R[n]); // operand1 = UInt(R[n]) produces the same final results
    992         uint64_t operand1 = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
    993         if (!success)
    994             return false;
    995 
    996         // operand2 = SInt(R[m]); // operand2 = UInt(R[m]) produces the same final results
    997         uint64_t operand2 = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
    998         if (!success)
    999             return false;
   1000 
   1001         // result = operand1 * operand2;
   1002         uint64_t result = operand1 * operand2;
   1003 
   1004         // R[d] = result<31:0>;
   1005         RegisterInfo op1_reg;
   1006         RegisterInfo op2_reg;
   1007         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, op1_reg);
   1008         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, op2_reg);
   1009 
   1010         EmulateInstruction::Context context;
   1011         context.type = eContextArithmetic;
   1012         context.SetRegisterRegisterOperands (op1_reg, op2_reg);
   1013 
   1014         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, (0x0000ffff & result)))
   1015             return false;
   1016 
   1017         // if setflags then
   1018         if (setflags)
   1019         {
   1020             // APSR.N = result<31>;
   1021             // APSR.Z = IsZeroBit(result);
   1022             m_new_inst_cpsr = m_opcode_cpsr;
   1023             SetBit32 (m_new_inst_cpsr, CPSR_N_POS, Bit32 (result, 31));
   1024             SetBit32 (m_new_inst_cpsr, CPSR_Z_POS, result == 0 ? 1 : 0);
   1025             if (m_new_inst_cpsr != m_opcode_cpsr)
   1026             {
   1027                 if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FLAGS, m_new_inst_cpsr))
   1028                     return false;
   1029             }
   1030 
   1031             // if ArchVersion() == 4 then
   1032                 // APSR.C = bit UNKNOWN;
   1033         }
   1034     }
   1035     return true;
   1036 }
   1037 
   1038 // Bitwise NOT (immediate) writes the bitwise inverse of an immediate value to the destination register.
   1039 // It can optionally update the condition flags based on the value.
   1040 bool
   1041 EmulateInstructionARM::EmulateMVNImm (const uint32_t opcode, const ARMEncoding encoding)
   1042 {
   1043 #if 0
   1044     // ARM pseudo code...
   1045     if (ConditionPassed())
   1046     {
   1047         EncodingSpecificOperations();
   1048         result = NOT(imm32);
   1049         if d == 15 then         // Can only occur for ARM encoding
   1050             ALUWritePC(result); // setflags is always FALSE here
   1051         else
   1052             R[d] = result;
   1053             if setflags then
   1054                 APSR.N = result<31>;
   1055                 APSR.Z = IsZeroBit(result);
   1056                 APSR.C = carry;
   1057                 // APSR.V unchanged
   1058     }
   1059 #endif
   1060 
   1061     if (ConditionPassed(opcode))
   1062     {
   1063         uint32_t Rd; // the destination register
   1064         uint32_t imm32; // the output after ThumbExpandImm_C or ARMExpandImm_C
   1065         uint32_t carry; // the carry bit after ThumbExpandImm_C or ARMExpandImm_C
   1066         bool setflags;
   1067         switch (encoding) {
   1068         case eEncodingT1:
   1069             Rd = Bits32(opcode, 11, 8);
   1070             setflags = BitIsSet(opcode, 20);
   1071             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry);
   1072             break;
   1073         case eEncodingA1:
   1074             Rd = Bits32(opcode, 15, 12);
   1075             setflags = BitIsSet(opcode, 20);
   1076             imm32 = ARMExpandImm_C(opcode, APSR_C, carry);
   1077 
   1078             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   1079             if (Rd == 15 && setflags)
   1080                 return EmulateSUBSPcLrEtc (opcode, encoding);
   1081             break;
   1082         default:
   1083             return false;
   1084         }
   1085         uint32_t result = ~imm32;
   1086 
   1087         // The context specifies that an immediate is to be moved into Rd.
   1088         EmulateInstruction::Context context;
   1089         context.type = EmulateInstruction::eContextImmediate;
   1090         context.SetNoArgs ();
   1091 
   1092         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   1093             return false;
   1094     }
   1095     return true;
   1096 }
   1097 
   1098 // Bitwise NOT (register) writes the bitwise inverse of a register value to the destination register.
   1099 // It can optionally update the condition flags based on the result.
   1100 bool
   1101 EmulateInstructionARM::EmulateMVNReg (const uint32_t opcode, const ARMEncoding encoding)
   1102 {
   1103 #if 0
   1104     // ARM pseudo code...
   1105     if (ConditionPassed())
   1106     {
   1107         EncodingSpecificOperations();
   1108         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   1109         result = NOT(shifted);
   1110         if d == 15 then         // Can only occur for ARM encoding
   1111             ALUWritePC(result); // setflags is always FALSE here
   1112         else
   1113             R[d] = result;
   1114             if setflags then
   1115                 APSR.N = result<31>;
   1116                 APSR.Z = IsZeroBit(result);
   1117                 APSR.C = carry;
   1118                 // APSR.V unchanged
   1119     }
   1120 #endif
   1121 
   1122     if (ConditionPassed(opcode))
   1123     {
   1124         uint32_t Rm; // the source register
   1125         uint32_t Rd; // the destination register
   1126         ARM_ShifterType shift_t;
   1127         uint32_t shift_n; // the shift applied to the value read from Rm
   1128         bool setflags;
   1129         uint32_t carry; // the carry bit after the shift operation
   1130         switch (encoding) {
   1131         case eEncodingT1:
   1132             Rd = Bits32(opcode, 2, 0);
   1133             Rm = Bits32(opcode, 5, 3);
   1134             setflags = !InITBlock();
   1135             shift_t = SRType_LSL;
   1136             shift_n = 0;
   1137             if (InITBlock())
   1138                 return false;
   1139             break;
   1140         case eEncodingT2:
   1141             Rd = Bits32(opcode, 11, 8);
   1142             Rm = Bits32(opcode, 3, 0);
   1143             setflags = BitIsSet(opcode, 20);
   1144             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   1145             // if (BadReg(d) || BadReg(m)) then UNPREDICTABLE;
   1146             if (BadReg(Rd) || BadReg(Rm))
   1147                 return false;
   1148             break;
   1149         case eEncodingA1:
   1150             Rd = Bits32(opcode, 15, 12);
   1151             Rm = Bits32(opcode, 3, 0);
   1152             setflags = BitIsSet(opcode, 20);
   1153             shift_n = DecodeImmShiftARM(opcode, shift_t);
   1154             break;
   1155         default:
   1156             return false;
   1157         }
   1158         bool success = false;
   1159         uint32_t value = ReadCoreReg(Rm, &success);
   1160         if (!success)
   1161             return false;
   1162 
   1163         uint32_t shifted = Shift_C(value, shift_t, shift_n, APSR_C, carry, &success);
   1164         if (!success)
   1165             return false;
   1166         uint32_t result = ~shifted;
   1167 
   1168         // The context specifies that an immediate is to be moved into Rd.
   1169         EmulateInstruction::Context context;
   1170         context.type = EmulateInstruction::eContextImmediate;
   1171         context.SetNoArgs ();
   1172 
   1173         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   1174             return false;
   1175     }
   1176     return true;
   1177 }
   1178 
   1179 // PC relative immediate load into register, possibly followed by ADD (SP plus register).
   1180 // LDR (literal)
   1181 bool
   1182 EmulateInstructionARM::EmulateLDRRtPCRelative (const uint32_t opcode, const ARMEncoding encoding)
   1183 {
   1184 #if 0
   1185     // ARM pseudo code...
   1186     if (ConditionPassed())
   1187     {
   1188         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   1189         base = Align(PC,4);
   1190         address = if add then (base + imm32) else (base - imm32);
   1191         data = MemU[address,4];
   1192         if t == 15 then
   1193             if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   1194         elsif UnalignedSupport() || address<1:0> = '00' then
   1195             R[t] = data;
   1196         else // Can only apply before ARMv7
   1197             if CurrentInstrSet() == InstrSet_ARM then
   1198                 R[t] = ROR(data, 8*UInt(address<1:0>));
   1199             else
   1200                 R[t] = bits(32) UNKNOWN;
   1201     }
   1202 #endif
   1203 
   1204     if (ConditionPassed(opcode))
   1205     {
   1206         bool success = false;
   1207         const uint32_t pc = ReadCoreReg(PC_REG, &success);
   1208         if (!success)
   1209             return false;
   1210 
   1211         // PC relative immediate load context
   1212         EmulateInstruction::Context context;
   1213         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   1214         RegisterInfo pc_reg;
   1215         GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, pc_reg);
   1216         context.SetRegisterPlusOffset (pc_reg, 0);
   1217 
   1218         uint32_t Rt;    // the destination register
   1219         uint32_t imm32; // immediate offset from the PC
   1220         bool add;       // +imm32 or -imm32?
   1221         addr_t base;    // the base address
   1222         addr_t address; // the PC relative address
   1223         uint32_t data;  // the literal data value from the PC relative load
   1224         switch (encoding) {
   1225         case eEncodingT1:
   1226             Rt = Bits32(opcode, 10, 8);
   1227             imm32 = Bits32(opcode, 7, 0) << 2; // imm32 = ZeroExtend(imm8:'00', 32);
   1228             add = true;
   1229             break;
   1230         case eEncodingT2:
   1231             Rt = Bits32(opcode, 15, 12);
   1232             imm32 = Bits32(opcode, 11, 0) << 2; // imm32 = ZeroExtend(imm12, 32);
   1233             add = BitIsSet(opcode, 23);
   1234             if (Rt == 15 && InITBlock() && !LastInITBlock())
   1235                 return false;
   1236             break;
   1237         default:
   1238             return false;
   1239         }
   1240 
   1241         base = Align(pc, 4);
   1242         if (add)
   1243             address = base + imm32;
   1244         else
   1245             address = base - imm32;
   1246 
   1247         context.SetRegisterPlusOffset(pc_reg, address - base);
   1248         data = MemURead(context, address, 4, 0, &success);
   1249         if (!success)
   1250             return false;
   1251 
   1252         if (Rt == 15)
   1253         {
   1254             if (Bits32(address, 1, 0) == 0)
   1255             {
   1256                 // In ARMv5T and above, this is an interworking branch.
   1257                 if (!LoadWritePC(context, data))
   1258                     return false;
   1259             }
   1260             else
   1261                 return false;
   1262         }
   1263         else if (UnalignedSupport() || Bits32(address, 1, 0) == 0)
   1264         {
   1265             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + Rt, data))
   1266                 return false;
   1267         }
   1268         else // We don't handle ARM for now.
   1269             return false;
   1270 
   1271     }
   1272     return true;
   1273 }
   1274 
   1275 // An add operation to adjust the SP.
   1276 // ADD (SP plus immediate)
   1277 bool
   1278 EmulateInstructionARM::EmulateADDSPImm (const uint32_t opcode, const ARMEncoding encoding)
   1279 {
   1280 #if 0
   1281     // ARM pseudo code...
   1282     if (ConditionPassed())
   1283     {
   1284         EncodingSpecificOperations();
   1285         (result, carry, overflow) = AddWithCarry(SP, imm32, '0');
   1286         if d == 15 then // Can only occur for ARM encoding
   1287             ALUWritePC(result); // setflags is always FALSE here
   1288         else
   1289             R[d] = result;
   1290             if setflags then
   1291                 APSR.N = result<31>;
   1292                 APSR.Z = IsZeroBit(result);
   1293                 APSR.C = carry;
   1294                 APSR.V = overflow;
   1295     }
   1296 #endif
   1297 
   1298     bool success = false;
   1299 
   1300     if (ConditionPassed(opcode))
   1301     {
   1302         const addr_t sp = ReadCoreReg (SP_REG, &success);
   1303         if (!success)
   1304             return false;
   1305         uint32_t imm32; // the immediate operand
   1306         uint32_t d;
   1307         //bool setflags = false; // Add this back if/when support eEncodingT3 eEncodingA1
   1308         switch (encoding)
   1309         {
   1310             case eEncodingT1:
   1311                 // d = UInt(Rd); setflags = FALSE; imm32 = ZeroExtend(imm8:'00', 32);
   1312                 d = Bits32 (opcode, 10, 8);
   1313                 imm32 = (Bits32 (opcode, 7, 0) << 2);
   1314 
   1315                 break;
   1316 
   1317             case eEncodingT2:
   1318                 // d = 13; setflags = FALSE; imm32 = ZeroExtend(imm7:'00', 32);
   1319                 d = 13;
   1320                 imm32 = ThumbImm7Scaled(opcode); // imm32 = ZeroExtend(imm7:'00', 32)
   1321 
   1322                 break;
   1323 
   1324             default:
   1325                 return false;
   1326         }
   1327         addr_t sp_offset = imm32;
   1328         addr_t addr = sp + sp_offset; // the adjusted stack pointer value
   1329 
   1330         EmulateInstruction::Context context;
   1331         context.type = EmulateInstruction::eContextAdjustStackPointer;
   1332         RegisterInfo sp_reg;
   1333         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   1334         context.SetRegisterPlusOffset (sp_reg, sp_offset);
   1335 
   1336         if (d == 15)
   1337         {
   1338             if (!ALUWritePC (context, addr))
   1339                 return false;
   1340         }
   1341         else
   1342         {
   1343             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, addr))
   1344                 return false;
   1345 
   1346             // Add this back if/when support eEncodingT3 eEncodingA1
   1347             //if (setflags)
   1348             //{
   1349             //    APSR.N = result<31>;
   1350             //    APSR.Z = IsZeroBit(result);
   1351             //    APSR.C = carry;
   1352             //    APSR.V = overflow;
   1353             //}
   1354         }
   1355     }
   1356     return true;
   1357 }
   1358 
   1359 // An add operation to adjust the SP.
   1360 // ADD (SP plus register)
   1361 bool
   1362 EmulateInstructionARM::EmulateADDSPRm (const uint32_t opcode, const ARMEncoding encoding)
   1363 {
   1364 #if 0
   1365     // ARM pseudo code...
   1366     if (ConditionPassed())
   1367     {
   1368         EncodingSpecificOperations();
   1369         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   1370         (result, carry, overflow) = AddWithCarry(SP, shifted, '0');
   1371         if d == 15 then
   1372             ALUWritePC(result); // setflags is always FALSE here
   1373         else
   1374             R[d] = result;
   1375             if setflags then
   1376                 APSR.N = result<31>;
   1377                 APSR.Z = IsZeroBit(result);
   1378                 APSR.C = carry;
   1379                 APSR.V = overflow;
   1380     }
   1381 #endif
   1382 
   1383     bool success = false;
   1384 
   1385     if (ConditionPassed(opcode))
   1386     {
   1387         const addr_t sp = ReadCoreReg (SP_REG, &success);
   1388         if (!success)
   1389             return false;
   1390         uint32_t Rm; // the second operand
   1391         switch (encoding) {
   1392         case eEncodingT2:
   1393             Rm = Bits32(opcode, 6, 3);
   1394             break;
   1395         default:
   1396             return false;
   1397         }
   1398         int32_t reg_value = ReadCoreReg(Rm, &success);
   1399         if (!success)
   1400             return false;
   1401 
   1402         addr_t addr = (int32_t)sp + reg_value; // the adjusted stack pointer value
   1403 
   1404         EmulateInstruction::Context context;
   1405         context.type = eContextArithmetic;
   1406         RegisterInfo sp_reg;
   1407         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   1408 
   1409         RegisterInfo other_reg;
   1410         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, other_reg);
   1411         context.SetRegisterRegisterOperands (sp_reg, other_reg);
   1412 
   1413         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, addr))
   1414             return false;
   1415     }
   1416     return true;
   1417 }
   1418 
   1419 // Branch with Link and Exchange Instruction Sets (immediate) calls a subroutine
   1420 // at a PC-relative address, and changes instruction set from ARM to Thumb, or
   1421 // from Thumb to ARM.
   1422 // BLX (immediate)
   1423 bool
   1424 EmulateInstructionARM::EmulateBLXImmediate (const uint32_t opcode, const ARMEncoding encoding)
   1425 {
   1426 #if 0
   1427     // ARM pseudo code...
   1428     if (ConditionPassed())
   1429     {
   1430         EncodingSpecificOperations();
   1431         if CurrentInstrSet() == InstrSet_ARM then
   1432             LR = PC - 4;
   1433         else
   1434             LR = PC<31:1> : '1';
   1435         if targetInstrSet == InstrSet_ARM then
   1436             targetAddress = Align(PC,4) + imm32;
   1437         else
   1438             targetAddress = PC + imm32;
   1439         SelectInstrSet(targetInstrSet);
   1440         BranchWritePC(targetAddress);
   1441     }
   1442 #endif
   1443 
   1444     bool success = true;
   1445 
   1446     if (ConditionPassed(opcode))
   1447     {
   1448         EmulateInstruction::Context context;
   1449         context.type = EmulateInstruction::eContextRelativeBranchImmediate;
   1450         const uint32_t pc = ReadCoreReg(PC_REG, &success);
   1451         if (!success)
   1452             return false;
   1453         addr_t lr; // next instruction address
   1454         addr_t target; // target address
   1455         int32_t imm32; // PC-relative offset
   1456         switch (encoding) {
   1457         case eEncodingT1:
   1458             {
   1459             lr = pc | 1u; // return address
   1460             uint32_t S = Bit32(opcode, 26);
   1461             uint32_t imm10 = Bits32(opcode, 25, 16);
   1462             uint32_t J1 = Bit32(opcode, 13);
   1463             uint32_t J2 = Bit32(opcode, 11);
   1464             uint32_t imm11 = Bits32(opcode, 10, 0);
   1465             uint32_t I1 = !(J1 ^ S);
   1466             uint32_t I2 = !(J2 ^ S);
   1467             uint32_t imm25 = (S << 24) | (I1 << 23) | (I2 << 22) | (imm10 << 12) | (imm11 << 1);
   1468             imm32 = llvm::SignExtend32<25>(imm25);
   1469             target = pc + imm32;
   1470             context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   1471             if (InITBlock() && !LastInITBlock())
   1472                 return false;
   1473             break;
   1474             }
   1475         case eEncodingT2:
   1476             {
   1477             lr = pc | 1u; // return address
   1478             uint32_t S = Bit32(opcode, 26);
   1479             uint32_t imm10H = Bits32(opcode, 25, 16);
   1480             uint32_t J1 = Bit32(opcode, 13);
   1481             uint32_t J2 = Bit32(opcode, 11);
   1482             uint32_t imm10L = Bits32(opcode, 10, 1);
   1483             uint32_t I1 = !(J1 ^ S);
   1484             uint32_t I2 = !(J2 ^ S);
   1485             uint32_t imm25 = (S << 24) | (I1 << 23) | (I2 << 22) | (imm10H << 12) | (imm10L << 2);
   1486             imm32 = llvm::SignExtend32<25>(imm25);
   1487             target = Align(pc, 4) + imm32;
   1488             context.SetISAAndImmediateSigned (eModeARM, 4 + imm32);
   1489             if (InITBlock() && !LastInITBlock())
   1490                 return false;
   1491             break;
   1492             }
   1493         case eEncodingA1:
   1494             lr = pc - 4; // return address
   1495             imm32 = llvm::SignExtend32<26>(Bits32(opcode, 23, 0) << 2);
   1496             target = Align(pc, 4) + imm32;
   1497             context.SetISAAndImmediateSigned (eModeARM, 8 + imm32);
   1498             break;
   1499         case eEncodingA2:
   1500             lr = pc - 4; // return address
   1501             imm32 = llvm::SignExtend32<26>(Bits32(opcode, 23, 0) << 2 | Bits32(opcode, 24, 24) << 1);
   1502             target = pc + imm32;
   1503             context.SetISAAndImmediateSigned (eModeThumb, 8 + imm32);
   1504             break;
   1505         default:
   1506             return false;
   1507         }
   1508         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_RA, lr))
   1509             return false;
   1510         if (!BranchWritePC(context, target))
   1511             return false;
   1512     }
   1513     return true;
   1514 }
   1515 
   1516 // Branch with Link and Exchange (register) calls a subroutine at an address and
   1517 // instruction set specified by a register.
   1518 // BLX (register)
   1519 bool
   1520 EmulateInstructionARM::EmulateBLXRm (const uint32_t opcode, const ARMEncoding encoding)
   1521 {
   1522 #if 0
   1523     // ARM pseudo code...
   1524     if (ConditionPassed())
   1525     {
   1526         EncodingSpecificOperations();
   1527         target = R[m];
   1528         if CurrentInstrSet() == InstrSet_ARM then
   1529             next_instr_addr = PC - 4;
   1530             LR = next_instr_addr;
   1531         else
   1532             next_instr_addr = PC - 2;
   1533             LR = next_instr_addr<31:1> : '1';
   1534         BXWritePC(target);
   1535     }
   1536 #endif
   1537 
   1538     bool success = false;
   1539 
   1540     if (ConditionPassed(opcode))
   1541     {
   1542         EmulateInstruction::Context context;
   1543         context.type = EmulateInstruction::eContextAbsoluteBranchRegister;
   1544         const uint32_t pc = ReadCoreReg(PC_REG, &success);
   1545         addr_t lr; // next instruction address
   1546         if (!success)
   1547             return false;
   1548         uint32_t Rm; // the register with the target address
   1549         switch (encoding) {
   1550         case eEncodingT1:
   1551             lr = (pc - 2) | 1u; // return address
   1552             Rm = Bits32(opcode, 6, 3);
   1553             // if m == 15 then UNPREDICTABLE;
   1554             if (Rm == 15)
   1555                 return false;
   1556             if (InITBlock() && !LastInITBlock())
   1557                 return false;
   1558             break;
   1559         case eEncodingA1:
   1560             lr = pc - 4; // return address
   1561             Rm = Bits32(opcode, 3, 0);
   1562             // if m == 15 then UNPREDICTABLE;
   1563             if (Rm == 15)
   1564                 return false;
   1565             break;
   1566         default:
   1567             return false;
   1568         }
   1569         addr_t target = ReadCoreReg (Rm, &success);
   1570         if (!success)
   1571             return false;
   1572         RegisterInfo dwarf_reg;
   1573         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, dwarf_reg);
   1574         context.SetRegister (dwarf_reg);
   1575         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_RA, lr))
   1576             return false;
   1577         if (!BXWritePC(context, target))
   1578             return false;
   1579     }
   1580     return true;
   1581 }
   1582 
   1583 // Branch and Exchange causes a branch to an address and instruction set specified by a register.
   1584 bool
   1585 EmulateInstructionARM::EmulateBXRm (const uint32_t opcode, const ARMEncoding encoding)
   1586 {
   1587 #if 0
   1588     // ARM pseudo code...
   1589     if (ConditionPassed())
   1590     {
   1591         EncodingSpecificOperations();
   1592         BXWritePC(R[m]);
   1593     }
   1594 #endif
   1595 
   1596     if (ConditionPassed(opcode))
   1597     {
   1598         EmulateInstruction::Context context;
   1599         context.type = EmulateInstruction::eContextAbsoluteBranchRegister;
   1600         uint32_t Rm; // the register with the target address
   1601         switch (encoding) {
   1602         case eEncodingT1:
   1603             Rm = Bits32(opcode, 6, 3);
   1604             if (InITBlock() && !LastInITBlock())
   1605                 return false;
   1606             break;
   1607         case eEncodingA1:
   1608             Rm = Bits32(opcode, 3, 0);
   1609             break;
   1610         default:
   1611             return false;
   1612         }
   1613         bool success = false;
   1614         addr_t target = ReadCoreReg (Rm, &success);
   1615         if (!success)
   1616             return false;
   1617 
   1618         RegisterInfo dwarf_reg;
   1619         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, dwarf_reg);
   1620         context.SetRegister (dwarf_reg);
   1621         if (!BXWritePC(context, target))
   1622             return false;
   1623     }
   1624     return true;
   1625 }
   1626 
   1627 // Branch and Exchange Jazelle attempts to change to Jazelle state. If the attempt fails, it branches to an
   1628 // address and instruction set specified by a register as though it were a BX instruction.
   1629 //
   1630 // TODO: Emulate Jazelle architecture?
   1631 //       We currently assume that switching to Jazelle state fails, thus treating BXJ as a BX operation.
   1632 bool
   1633 EmulateInstructionARM::EmulateBXJRm (const uint32_t opcode, const ARMEncoding encoding)
   1634 {
   1635 #if 0
   1636     // ARM pseudo code...
   1637     if (ConditionPassed())
   1638     {
   1639         EncodingSpecificOperations();
   1640         if JMCR.JE == '0' || CurrentInstrSet() == InstrSet_ThumbEE then
   1641             BXWritePC(R[m]);
   1642         else
   1643             if JazelleAcceptsExecution() then
   1644                 SwitchToJazelleExecution();
   1645             else
   1646                 SUBARCHITECTURE_DEFINED handler call;
   1647     }
   1648 #endif
   1649 
   1650     if (ConditionPassed(opcode))
   1651     {
   1652         EmulateInstruction::Context context;
   1653         context.type = EmulateInstruction::eContextAbsoluteBranchRegister;
   1654         uint32_t Rm; // the register with the target address
   1655         switch (encoding) {
   1656         case eEncodingT1:
   1657             Rm = Bits32(opcode, 19, 16);
   1658             if (BadReg(Rm))
   1659                 return false;
   1660             if (InITBlock() && !LastInITBlock())
   1661                 return false;
   1662             break;
   1663         case eEncodingA1:
   1664             Rm = Bits32(opcode, 3, 0);
   1665             if (Rm == 15)
   1666                 return false;
   1667             break;
   1668         default:
   1669             return false;
   1670         }
   1671         bool success = false;
   1672         addr_t target = ReadCoreReg (Rm, &success);
   1673         if (!success)
   1674             return false;
   1675 
   1676         RegisterInfo dwarf_reg;
   1677         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, dwarf_reg);
   1678         context.SetRegister (dwarf_reg);
   1679         if (!BXWritePC(context, target))
   1680             return false;
   1681     }
   1682     return true;
   1683 }
   1684 
   1685 // Set r7 to point to some ip offset.
   1686 // SUB (immediate)
   1687 bool
   1688 EmulateInstructionARM::EmulateSUBR7IPImm (const uint32_t opcode, const ARMEncoding encoding)
   1689 {
   1690 #if 0
   1691     // ARM pseudo code...
   1692     if (ConditionPassed())
   1693     {
   1694         EncodingSpecificOperations();
   1695         (result, carry, overflow) = AddWithCarry(SP, NOT(imm32), '1');
   1696         if d == 15 then // Can only occur for ARM encoding
   1697            ALUWritePC(result); // setflags is always FALSE here
   1698         else
   1699             R[d] = result;
   1700             if setflags then
   1701                 APSR.N = result<31>;
   1702                 APSR.Z = IsZeroBit(result);
   1703                 APSR.C = carry;
   1704                 APSR.V = overflow;
   1705     }
   1706 #endif
   1707 
   1708     if (ConditionPassed(opcode))
   1709     {
   1710         bool success = false;
   1711         const addr_t ip = ReadCoreReg (12, &success);
   1712         if (!success)
   1713             return false;
   1714         uint32_t imm32;
   1715         switch (encoding) {
   1716         case eEncodingA1:
   1717             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   1718             break;
   1719         default:
   1720             return false;
   1721         }
   1722         addr_t ip_offset = imm32;
   1723         addr_t addr = ip - ip_offset; // the adjusted ip value
   1724 
   1725         EmulateInstruction::Context context;
   1726         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   1727         RegisterInfo dwarf_reg;
   1728         GetRegisterInfo (eRegisterKindDWARF, dwarf_r12, dwarf_reg);
   1729         context.SetRegisterPlusOffset (dwarf_reg, -ip_offset);
   1730 
   1731         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r7, addr))
   1732             return false;
   1733     }
   1734     return true;
   1735 }
   1736 
   1737 // Set ip to point to some stack offset.
   1738 // SUB (SP minus immediate)
   1739 bool
   1740 EmulateInstructionARM::EmulateSUBIPSPImm (const uint32_t opcode, const ARMEncoding encoding)
   1741 {
   1742 #if 0
   1743     // ARM pseudo code...
   1744     if (ConditionPassed())
   1745     {
   1746         EncodingSpecificOperations();
   1747         (result, carry, overflow) = AddWithCarry(SP, NOT(imm32), '1');
   1748         if d == 15 then // Can only occur for ARM encoding
   1749            ALUWritePC(result); // setflags is always FALSE here
   1750         else
   1751             R[d] = result;
   1752             if setflags then
   1753                 APSR.N = result<31>;
   1754                 APSR.Z = IsZeroBit(result);
   1755                 APSR.C = carry;
   1756                 APSR.V = overflow;
   1757     }
   1758 #endif
   1759 
   1760     if (ConditionPassed(opcode))
   1761     {
   1762         bool success = false;
   1763         const addr_t sp = ReadCoreReg (SP_REG, &success);
   1764         if (!success)
   1765             return false;
   1766         uint32_t imm32;
   1767         switch (encoding) {
   1768         case eEncodingA1:
   1769             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   1770             break;
   1771         default:
   1772             return false;
   1773         }
   1774         addr_t sp_offset = imm32;
   1775         addr_t addr = sp - sp_offset; // the adjusted stack pointer value
   1776 
   1777         EmulateInstruction::Context context;
   1778         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   1779         RegisterInfo dwarf_reg;
   1780         GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, dwarf_reg);
   1781         context.SetRegisterPlusOffset (dwarf_reg, -sp_offset);
   1782 
   1783         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r12, addr))
   1784             return false;
   1785     }
   1786     return true;
   1787 }
   1788 
   1789 // This instruction subtracts an immediate value from the SP value, and writes
   1790 // the result to the destination register.
   1791 //
   1792 // If Rd == 13 => A sub operation to adjust the SP -- allocate space for local storage.
   1793 bool
   1794 EmulateInstructionARM::EmulateSUBSPImm (const uint32_t opcode, const ARMEncoding encoding)
   1795 {
   1796 #if 0
   1797     // ARM pseudo code...
   1798     if (ConditionPassed())
   1799     {
   1800         EncodingSpecificOperations();
   1801         (result, carry, overflow) = AddWithCarry(SP, NOT(imm32), '1');
   1802         if d == 15 then        // Can only occur for ARM encoding
   1803            ALUWritePC(result); // setflags is always FALSE here
   1804         else
   1805             R[d] = result;
   1806             if setflags then
   1807                 APSR.N = result<31>;
   1808                 APSR.Z = IsZeroBit(result);
   1809                 APSR.C = carry;
   1810                 APSR.V = overflow;
   1811     }
   1812 #endif
   1813 
   1814     bool success = false;
   1815     if (ConditionPassed(opcode))
   1816     {
   1817         const addr_t sp = ReadCoreReg (SP_REG, &success);
   1818         if (!success)
   1819             return false;
   1820 
   1821         uint32_t Rd;
   1822         bool setflags;
   1823         uint32_t imm32;
   1824         switch (encoding) {
   1825         case eEncodingT1:
   1826             Rd = 13;
   1827             setflags = false;
   1828             imm32 = ThumbImm7Scaled(opcode); // imm32 = ZeroExtend(imm7:'00', 32)
   1829             break;
   1830         case eEncodingT2:
   1831             Rd = Bits32(opcode, 11, 8);
   1832             setflags = BitIsSet(opcode, 20);
   1833             imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   1834             if (Rd == 15 && setflags)
   1835                 return EmulateCMPImm(opcode, eEncodingT2);
   1836             if (Rd == 15 && !setflags)
   1837                 return false;
   1838             break;
   1839         case eEncodingT3:
   1840             Rd = Bits32(opcode, 11, 8);
   1841             setflags = false;
   1842             imm32 = ThumbImm12(opcode); // imm32 = ZeroExtend(i:imm3:imm8, 32)
   1843             if (Rd == 15)
   1844                 return false;
   1845             break;
   1846         case eEncodingA1:
   1847             Rd = Bits32(opcode, 15, 12);
   1848             setflags = BitIsSet(opcode, 20);
   1849             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   1850 
   1851             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   1852             if (Rd == 15 && setflags)
   1853                 return EmulateSUBSPcLrEtc (opcode, encoding);
   1854             break;
   1855         default:
   1856             return false;
   1857         }
   1858         AddWithCarryResult res = AddWithCarry(sp, ~imm32, 1);
   1859 
   1860         EmulateInstruction::Context context;
   1861         if (Rd == 13)
   1862         {
   1863             uint64_t imm64 = imm32;  // Need to expand it to 64 bits before attempting to negate it, or the wrong
   1864                                      // value gets passed down to context.SetImmediateSigned.
   1865             context.type = EmulateInstruction::eContextAdjustStackPointer;
   1866             context.SetImmediateSigned (-imm64); // the stack pointer offset
   1867         }
   1868         else
   1869         {
   1870             context.type = EmulateInstruction::eContextImmediate;
   1871             context.SetNoArgs ();
   1872         }
   1873 
   1874         if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   1875             return false;
   1876     }
   1877     return true;
   1878 }
   1879 
   1880 // A store operation to the stack that also updates the SP.
   1881 bool
   1882 EmulateInstructionARM::EmulateSTRRtSP (const uint32_t opcode, const ARMEncoding encoding)
   1883 {
   1884 #if 0
   1885     // ARM pseudo code...
   1886     if (ConditionPassed())
   1887     {
   1888         EncodingSpecificOperations();
   1889         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   1890         address = if index then offset_addr else R[n];
   1891         MemU[address,4] = if t == 15 then PCStoreValue() else R[t];
   1892         if wback then R[n] = offset_addr;
   1893     }
   1894 #endif
   1895 
   1896     bool conditional = false;
   1897     bool success = false;
   1898     if (ConditionPassed(opcode, &conditional))
   1899     {
   1900         const uint32_t addr_byte_size = GetAddressByteSize();
   1901         const addr_t sp = ReadCoreReg (SP_REG, &success);
   1902         if (!success)
   1903             return false;
   1904         uint32_t Rt; // the source register
   1905         uint32_t imm12;
   1906         uint32_t Rn;  // This function assumes Rn is the SP, but we should verify that.
   1907 
   1908         bool index;
   1909         bool add;
   1910         bool wback;
   1911         switch (encoding) {
   1912         case eEncodingA1:
   1913             Rt = Bits32(opcode, 15, 12);
   1914             imm12 = Bits32(opcode, 11, 0);
   1915             Rn = Bits32 (opcode, 19, 16);
   1916 
   1917             if (Rn != 13) // 13 is the SP reg on ARM.  Verify that Rn == SP.
   1918                 return false;
   1919 
   1920             index = BitIsSet (opcode, 24);
   1921             add = BitIsSet (opcode, 23);
   1922             wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   1923 
   1924             if (wback && ((Rn == 15) || (Rn == Rt)))
   1925                 return false;
   1926             break;
   1927         default:
   1928             return false;
   1929         }
   1930         addr_t offset_addr;
   1931         if (add)
   1932             offset_addr = sp + imm12;
   1933         else
   1934             offset_addr = sp - imm12;
   1935 
   1936         addr_t addr;
   1937         if (index)
   1938             addr = offset_addr;
   1939         else
   1940             addr = sp;
   1941 
   1942         EmulateInstruction::Context context;
   1943         if (conditional)
   1944             context.type = EmulateInstruction::eContextRegisterStore;
   1945         else
   1946             context.type = EmulateInstruction::eContextPushRegisterOnStack;
   1947         RegisterInfo sp_reg;
   1948         RegisterInfo dwarf_reg;
   1949 
   1950         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   1951         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rt, dwarf_reg);
   1952         context.SetRegisterToRegisterPlusOffset ( dwarf_reg, sp_reg, addr - sp);
   1953         if (Rt != 15)
   1954         {
   1955             uint32_t reg_value = ReadCoreReg(Rt, &success);
   1956             if (!success)
   1957                 return false;
   1958             if (!MemUWrite (context, addr, reg_value, addr_byte_size))
   1959                 return false;
   1960         }
   1961         else
   1962         {
   1963             const uint32_t pc = ReadCoreReg(PC_REG, &success);
   1964             if (!success)
   1965                 return false;
   1966             if (!MemUWrite (context, addr, pc, addr_byte_size))
   1967                 return false;
   1968         }
   1969 
   1970 
   1971         if (wback)
   1972         {
   1973             context.type = EmulateInstruction::eContextAdjustStackPointer;
   1974             context.SetImmediateSigned (addr - sp);
   1975             if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, offset_addr))
   1976                 return false;
   1977         }
   1978     }
   1979     return true;
   1980 }
   1981 
   1982 // Vector Push stores multiple extension registers to the stack.
   1983 // It also updates SP to point to the start of the stored data.
   1984 bool
   1985 EmulateInstructionARM::EmulateVPUSH (const uint32_t opcode, const ARMEncoding encoding)
   1986 {
   1987 #if 0
   1988     // ARM pseudo code...
   1989     if (ConditionPassed())
   1990     {
   1991         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(13);
   1992         address = SP - imm32;
   1993         SP = SP - imm32;
   1994         if single_regs then
   1995             for r = 0 to regs-1
   1996                 MemA[address,4] = S[d+r]; address = address+4;
   1997         else
   1998             for r = 0 to regs-1
   1999                 // Store as two word-aligned words in the correct order for current endianness.
   2000                 MemA[address,4] = if BigEndian() then D[d+r]<63:32> else D[d+r]<31:0>;
   2001                 MemA[address+4,4] = if BigEndian() then D[d+r]<31:0> else D[d+r]<63:32>;
   2002                 address = address+8;
   2003     }
   2004 #endif
   2005 
   2006     bool success = false;
   2007     bool conditional = false;
   2008     if (ConditionPassed(opcode, &conditional))
   2009     {
   2010         const uint32_t addr_byte_size = GetAddressByteSize();
   2011         const addr_t sp = ReadCoreReg (SP_REG, &success);
   2012         if (!success)
   2013             return false;
   2014         bool single_regs;
   2015         uint32_t d;     // UInt(D:Vd) or UInt(Vd:D) starting register
   2016         uint32_t imm32; // stack offset
   2017         uint32_t regs;  // number of registers
   2018         switch (encoding) {
   2019         case eEncodingT1:
   2020         case eEncodingA1:
   2021             single_regs = false;
   2022             d = Bit32(opcode, 22) << 4 | Bits32(opcode, 15, 12);
   2023             imm32 = Bits32(opcode, 7, 0) * addr_byte_size;
   2024             // If UInt(imm8) is odd, see "FSTMX".
   2025             regs = Bits32(opcode, 7, 0) / 2;
   2026             // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   2027             if (regs == 0 || regs > 16 || (d + regs) > 32)
   2028                 return false;
   2029             break;
   2030         case eEncodingT2:
   2031         case eEncodingA2:
   2032             single_regs = true;
   2033             d = Bits32(opcode, 15, 12) << 1 | Bit32(opcode, 22);
   2034             imm32 = Bits32(opcode, 7, 0) * addr_byte_size;
   2035             regs = Bits32(opcode, 7, 0);
   2036             // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   2037             if (regs == 0 || regs > 16 || (d + regs) > 32)
   2038                 return false;
   2039             break;
   2040         default:
   2041             return false;
   2042         }
   2043         uint32_t start_reg = single_regs ? dwarf_s0 : dwarf_d0;
   2044         uint32_t reg_byte_size = single_regs ? addr_byte_size : addr_byte_size * 2;
   2045         addr_t sp_offset = imm32;
   2046         addr_t addr = sp - sp_offset;
   2047         uint32_t i;
   2048 
   2049         EmulateInstruction::Context context;
   2050         if (conditional)
   2051             context.type = EmulateInstruction::eContextRegisterStore;
   2052         else
   2053             context.type = EmulateInstruction::eContextPushRegisterOnStack;
   2054         RegisterInfo dwarf_reg;
   2055         RegisterInfo sp_reg;
   2056         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   2057         for (i=0; i<regs; ++i)
   2058         {
   2059             GetRegisterInfo (eRegisterKindDWARF, start_reg + d + i, dwarf_reg);
   2060             context.SetRegisterToRegisterPlusOffset ( dwarf_reg, sp_reg, addr - sp);
   2061             // uint64_t to accommodate 64-bit registers.
   2062             uint64_t reg_value = ReadRegisterUnsigned (&dwarf_reg, 0, &success);
   2063             if (!success)
   2064                 return false;
   2065             if (!MemAWrite (context, addr, reg_value, reg_byte_size))
   2066                 return false;
   2067             addr += reg_byte_size;
   2068         }
   2069 
   2070         context.type = EmulateInstruction::eContextAdjustStackPointer;
   2071         context.SetImmediateSigned (-sp_offset);
   2072 
   2073         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, sp - sp_offset))
   2074             return false;
   2075     }
   2076     return true;
   2077 }
   2078 
   2079 // Vector Pop loads multiple extension registers from the stack.
   2080 // It also updates SP to point just above the loaded data.
   2081 bool
   2082 EmulateInstructionARM::EmulateVPOP (const uint32_t opcode, const ARMEncoding encoding)
   2083 {
   2084 #if 0
   2085     // ARM pseudo code...
   2086     if (ConditionPassed())
   2087     {
   2088         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(13);
   2089         address = SP;
   2090         SP = SP + imm32;
   2091         if single_regs then
   2092             for r = 0 to regs-1
   2093                 S[d+r] = MemA[address,4]; address = address+4;
   2094         else
   2095             for r = 0 to regs-1
   2096                 word1 = MemA[address,4]; word2 = MemA[address+4,4]; address = address+8;
   2097                 // Combine the word-aligned words in the correct order for current endianness.
   2098                 D[d+r] = if BigEndian() then word1:word2 else word2:word1;
   2099     }
   2100 #endif
   2101 
   2102     bool success = false;
   2103     bool conditional = false;
   2104     if (ConditionPassed(opcode, &conditional))
   2105     {
   2106         const uint32_t addr_byte_size = GetAddressByteSize();
   2107         const addr_t sp = ReadCoreReg (SP_REG, &success);
   2108         if (!success)
   2109             return false;
   2110         bool single_regs;
   2111         uint32_t d;     // UInt(D:Vd) or UInt(Vd:D) starting register
   2112         uint32_t imm32; // stack offset
   2113         uint32_t regs;  // number of registers
   2114         switch (encoding) {
   2115         case eEncodingT1:
   2116         case eEncodingA1:
   2117             single_regs = false;
   2118             d = Bit32(opcode, 22) << 4 | Bits32(opcode, 15, 12);
   2119             imm32 = Bits32(opcode, 7, 0) * addr_byte_size;
   2120             // If UInt(imm8) is odd, see "FLDMX".
   2121             regs = Bits32(opcode, 7, 0) / 2;
   2122             // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   2123             if (regs == 0 || regs > 16 || (d + regs) > 32)
   2124                 return false;
   2125             break;
   2126         case eEncodingT2:
   2127         case eEncodingA2:
   2128             single_regs = true;
   2129             d = Bits32(opcode, 15, 12) << 1 | Bit32(opcode, 22);
   2130             imm32 = Bits32(opcode, 7, 0) * addr_byte_size;
   2131             regs = Bits32(opcode, 7, 0);
   2132             // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   2133             if (regs == 0 || regs > 16 || (d + regs) > 32)
   2134                 return false;
   2135             break;
   2136         default:
   2137             return false;
   2138         }
   2139         uint32_t start_reg = single_regs ? dwarf_s0 : dwarf_d0;
   2140         uint32_t reg_byte_size = single_regs ? addr_byte_size : addr_byte_size * 2;
   2141         addr_t sp_offset = imm32;
   2142         addr_t addr = sp;
   2143         uint32_t i;
   2144         uint64_t data; // uint64_t to accomodate 64-bit registers.
   2145 
   2146         EmulateInstruction::Context context;
   2147         if (conditional)
   2148             context.type = EmulateInstruction::eContextRegisterLoad;
   2149         else
   2150             context.type = EmulateInstruction::eContextPopRegisterOffStack;
   2151         RegisterInfo dwarf_reg;
   2152         RegisterInfo sp_reg;
   2153         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   2154         for (i=0; i<regs; ++i)
   2155         {
   2156             GetRegisterInfo (eRegisterKindDWARF, start_reg + d + i, dwarf_reg);
   2157             context.SetRegisterPlusOffset (sp_reg, addr - sp);
   2158             data = MemARead(context, addr, reg_byte_size, 0, &success);
   2159             if (!success)
   2160                 return false;
   2161             if (!WriteRegisterUnsigned(context, &dwarf_reg, data))
   2162                 return false;
   2163             addr += reg_byte_size;
   2164         }
   2165 
   2166         context.type = EmulateInstruction::eContextAdjustStackPointer;
   2167         context.SetImmediateSigned (sp_offset);
   2168 
   2169         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, sp + sp_offset))
   2170             return false;
   2171     }
   2172     return true;
   2173 }
   2174 
   2175 // SVC (previously SWI)
   2176 bool
   2177 EmulateInstructionARM::EmulateSVC (const uint32_t opcode, const ARMEncoding encoding)
   2178 {
   2179 #if 0
   2180     // ARM pseudo code...
   2181     if (ConditionPassed())
   2182     {
   2183         EncodingSpecificOperations();
   2184         CallSupervisor();
   2185     }
   2186 #endif
   2187 
   2188     bool success = false;
   2189 
   2190     if (ConditionPassed(opcode))
   2191     {
   2192         const uint32_t pc = ReadCoreReg(PC_REG, &success);
   2193         addr_t lr; // next instruction address
   2194         if (!success)
   2195             return false;
   2196         uint32_t imm32; // the immediate constant
   2197         uint32_t mode;  // ARM or Thumb mode
   2198         switch (encoding) {
   2199         case eEncodingT1:
   2200             lr = (pc + 2) | 1u; // return address
   2201             imm32 = Bits32(opcode, 7, 0);
   2202             mode = eModeThumb;
   2203             break;
   2204         case eEncodingA1:
   2205             lr = pc + 4; // return address
   2206             imm32 = Bits32(opcode, 23, 0);
   2207             mode = eModeARM;
   2208             break;
   2209         default:
   2210             return false;
   2211         }
   2212 
   2213         EmulateInstruction::Context context;
   2214         context.type = EmulateInstruction::eContextSupervisorCall;
   2215         context.SetISAAndImmediate (mode, imm32);
   2216         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_RA, lr))
   2217             return false;
   2218     }
   2219     return true;
   2220 }
   2221 
   2222 // If Then makes up to four following instructions (the IT block) conditional.
   2223 bool
   2224 EmulateInstructionARM::EmulateIT (const uint32_t opcode, const ARMEncoding encoding)
   2225 {
   2226 #if 0
   2227     // ARM pseudo code...
   2228     EncodingSpecificOperations();
   2229     ITSTATE.IT<7:0> = firstcond:mask;
   2230 #endif
   2231 
   2232     m_it_session.InitIT(Bits32(opcode, 7, 0));
   2233     return true;
   2234 }
   2235 
   2236 bool
   2237 EmulateInstructionARM::EmulateNop (const uint32_t opcode, const ARMEncoding encoding)
   2238 {
   2239     // NOP, nothing to do...
   2240     return true;
   2241 }
   2242 
   2243 // Branch causes a branch to a target address.
   2244 bool
   2245 EmulateInstructionARM::EmulateB (const uint32_t opcode, const ARMEncoding encoding)
   2246 {
   2247 #if 0
   2248     // ARM pseudo code...
   2249     if (ConditionPassed())
   2250     {
   2251         EncodingSpecificOperations();
   2252         BranchWritePC(PC + imm32);
   2253     }
   2254 #endif
   2255 
   2256     bool success = false;
   2257 
   2258     if (ConditionPassed(opcode))
   2259     {
   2260         EmulateInstruction::Context context;
   2261         context.type = EmulateInstruction::eContextRelativeBranchImmediate;
   2262         const uint32_t pc = ReadCoreReg(PC_REG, &success);
   2263         if (!success)
   2264             return false;
   2265         addr_t target; // target address
   2266         int32_t imm32; // PC-relative offset
   2267         switch (encoding) {
   2268         case eEncodingT1:
   2269             // The 'cond' field is handled in EmulateInstructionARM::CurrentCond().
   2270             imm32 = llvm::SignExtend32<9>(Bits32(opcode, 7, 0) << 1);
   2271             target = pc + imm32;
   2272             context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   2273             break;
   2274         case eEncodingT2:
   2275             imm32 = llvm::SignExtend32<12>(Bits32(opcode, 10, 0));
   2276             target = pc + imm32;
   2277             context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   2278             break;
   2279         case eEncodingT3:
   2280             // The 'cond' field is handled in EmulateInstructionARM::CurrentCond().
   2281             {
   2282             uint32_t S = Bit32(opcode, 26);
   2283             uint32_t imm6 = Bits32(opcode, 21, 16);
   2284             uint32_t J1 = Bit32(opcode, 13);
   2285             uint32_t J2 = Bit32(opcode, 11);
   2286             uint32_t imm11 = Bits32(opcode, 10, 0);
   2287             uint32_t imm21 = (S << 20) | (J2 << 19) | (J1 << 18) | (imm6 << 12) | (imm11 << 1);
   2288             imm32 = llvm::SignExtend32<21>(imm21);
   2289             target = pc + imm32;
   2290             context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   2291             break;
   2292             }
   2293         case eEncodingT4:
   2294             {
   2295             uint32_t S = Bit32(opcode, 26);
   2296             uint32_t imm10 = Bits32(opcode, 25, 16);
   2297             uint32_t J1 = Bit32(opcode, 13);
   2298             uint32_t J2 = Bit32(opcode, 11);
   2299             uint32_t imm11 = Bits32(opcode, 10, 0);
   2300             uint32_t I1 = !(J1 ^ S);
   2301             uint32_t I2 = !(J2 ^ S);
   2302             uint32_t imm25 = (S << 24) | (I1 << 23) | (I2 << 22) | (imm10 << 12) | (imm11 << 1);
   2303             imm32 = llvm::SignExtend32<25>(imm25);
   2304             target = pc + imm32;
   2305             context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   2306             break;
   2307             }
   2308         case eEncodingA1:
   2309             imm32 = llvm::SignExtend32<26>(Bits32(opcode, 23, 0) << 2);
   2310             target = pc + imm32;
   2311             context.SetISAAndImmediateSigned (eModeARM, 8 + imm32);
   2312             break;
   2313         default:
   2314             return false;
   2315         }
   2316         if (!BranchWritePC(context, target))
   2317             return false;
   2318     }
   2319     return true;
   2320 }
   2321 
   2322 // Compare and Branch on Nonzero and Compare and Branch on Zero compare the value in a register with
   2323 // zero and conditionally branch forward a constant value.  They do not affect the condition flags.
   2324 // CBNZ, CBZ
   2325 bool
   2326 EmulateInstructionARM::EmulateCB (const uint32_t opcode, const ARMEncoding encoding)
   2327 {
   2328 #if 0
   2329     // ARM pseudo code...
   2330     EncodingSpecificOperations();
   2331     if nonzero ^ IsZero(R[n]) then
   2332         BranchWritePC(PC + imm32);
   2333 #endif
   2334 
   2335     bool success = false;
   2336 
   2337     // Read the register value from the operand register Rn.
   2338     uint32_t reg_val = ReadCoreReg(Bits32(opcode, 2, 0), &success);
   2339     if (!success)
   2340         return false;
   2341 
   2342     EmulateInstruction::Context context;
   2343     context.type = EmulateInstruction::eContextRelativeBranchImmediate;
   2344     const uint32_t pc = ReadCoreReg(PC_REG, &success);
   2345     if (!success)
   2346         return false;
   2347 
   2348     addr_t target;  // target address
   2349     uint32_t imm32; // PC-relative offset to branch forward
   2350     bool nonzero;
   2351     switch (encoding) {
   2352     case eEncodingT1:
   2353         imm32 = Bit32(opcode, 9) << 6 | Bits32(opcode, 7, 3) << 1;
   2354         nonzero = BitIsSet(opcode, 11);
   2355         target = pc + imm32;
   2356         context.SetISAAndImmediateSigned (eModeThumb, 4 + imm32);
   2357         break;
   2358     default:
   2359         return false;
   2360     }
   2361     if (nonzero ^ (reg_val == 0))
   2362         if (!BranchWritePC(context, target))
   2363             return false;
   2364 
   2365     return true;
   2366 }
   2367 
   2368 // Table Branch Byte causes a PC-relative forward branch using a table of single byte offsets.
   2369 // A base register provides a pointer to the table, and a second register supplies an index into the table.
   2370 // The branch length is twice the value of the byte returned from the table.
   2371 //
   2372 // Table Branch Halfword causes a PC-relative forward branch using a table of single halfword offsets.
   2373 // A base register provides a pointer to the table, and a second register supplies an index into the table.
   2374 // The branch length is twice the value of the halfword returned from the table.
   2375 // TBB, TBH
   2376 bool
   2377 EmulateInstructionARM::EmulateTB (const uint32_t opcode, const ARMEncoding encoding)
   2378 {
   2379 #if 0
   2380     // ARM pseudo code...
   2381     EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   2382     if is_tbh then
   2383         halfwords = UInt(MemU[R[n]+LSL(R[m],1), 2]);
   2384     else
   2385         halfwords = UInt(MemU[R[n]+R[m], 1]);
   2386     BranchWritePC(PC + 2*halfwords);
   2387 #endif
   2388 
   2389     bool success = false;
   2390 
   2391     uint32_t Rn;     // the base register which contains the address of the table of branch lengths
   2392     uint32_t Rm;     // the index register which contains an integer pointing to a byte/halfword in the table
   2393     bool is_tbh;     // true if table branch halfword
   2394     switch (encoding) {
   2395     case eEncodingT1:
   2396         Rn = Bits32(opcode, 19, 16);
   2397         Rm = Bits32(opcode, 3, 0);
   2398         is_tbh = BitIsSet(opcode, 4);
   2399         if (Rn == 13 || BadReg(Rm))
   2400             return false;
   2401         if (InITBlock() && !LastInITBlock())
   2402             return false;
   2403         break;
   2404     default:
   2405         return false;
   2406     }
   2407 
   2408     // Read the address of the table from the operand register Rn.
   2409     // The PC can be used, in which case the table immediately follows this instruction.
   2410     uint32_t base = ReadCoreReg(Rm, &success);
   2411     if (!success)
   2412         return false;
   2413 
   2414     // the table index
   2415     uint32_t index = ReadCoreReg(Rm, &success);
   2416     if (!success)
   2417         return false;
   2418 
   2419     // the offsetted table address
   2420     addr_t addr = base + (is_tbh ? index*2 : index);
   2421 
   2422     // PC-relative offset to branch forward
   2423     EmulateInstruction::Context context;
   2424     context.type = EmulateInstruction::eContextTableBranchReadMemory;
   2425     uint32_t offset = MemURead(context, addr, is_tbh ? 2 : 1, 0, &success) * 2;
   2426     if (!success)
   2427         return false;
   2428 
   2429     const uint32_t pc = ReadCoreReg(PC_REG, &success);
   2430     if (!success)
   2431         return false;
   2432 
   2433     // target address
   2434     addr_t target = pc + offset;
   2435     context.type = EmulateInstruction::eContextRelativeBranchImmediate;
   2436     context.SetISAAndImmediateSigned (eModeThumb, 4 + offset);
   2437 
   2438     if (!BranchWritePC(context, target))
   2439         return false;
   2440 
   2441     return true;
   2442 }
   2443 
   2444 // This instruction adds an immediate value to a register value, and writes the result to the destination register.
   2445 // It can optionally update the condition flags based on the result.
   2446 bool
   2447 EmulateInstructionARM::EmulateADDImmThumb (const uint32_t opcode, const ARMEncoding encoding)
   2448 {
   2449 #if 0
   2450     if ConditionPassed() then
   2451         EncodingSpecificOperations();
   2452         (result, carry, overflow) = AddWithCarry(R[n], imm32, '0');
   2453         R[d] = result;
   2454         if setflags then
   2455             APSR.N = result<31>;
   2456             APSR.Z = IsZeroBit(result);
   2457             APSR.C = carry;
   2458             APSR.V = overflow;
   2459 #endif
   2460 
   2461     bool success = false;
   2462 
   2463     if (ConditionPassed(opcode))
   2464     {
   2465         uint32_t d;
   2466         uint32_t n;
   2467         bool setflags;
   2468         uint32_t imm32;
   2469         uint32_t carry_out;
   2470 
   2471         //EncodingSpecificOperations();
   2472         switch (encoding)
   2473         {
   2474             case eEncodingT1:
   2475                 // d = UInt(Rd); n = UInt(Rn); setflags = !InITBlock(); imm32 = ZeroExtend(imm3, 32);
   2476                 d = Bits32 (opcode, 2, 0);
   2477                 n = Bits32 (opcode, 5, 3);
   2478                 setflags = !InITBlock();
   2479                 imm32 = Bits32 (opcode, 8,6);
   2480 
   2481                 break;
   2482 
   2483             case eEncodingT2:
   2484                 // d = UInt(Rdn); n = UInt(Rdn); setflags = !InITBlock(); imm32 = ZeroExtend(imm8, 32);
   2485                 d = Bits32 (opcode, 10, 8);
   2486                 n = Bits32 (opcode, 10, 8);
   2487                 setflags = !InITBlock();
   2488                 imm32 = Bits32 (opcode, 7, 0);
   2489 
   2490                 break;
   2491 
   2492             case eEncodingT3:
   2493                 // if Rd == '1111' && S == '1' then SEE CMN (immediate);
   2494                 // if Rn == '1101' then SEE ADD (SP plus immediate);
   2495                 // d = UInt(Rd); n = UInt(Rn); setflags = (S == '1'); imm32 = ThumbExpandImm(i:imm3:imm8);
   2496                 d = Bits32 (opcode, 11, 8);
   2497                 n = Bits32 (opcode, 19, 16);
   2498                 setflags = BitIsSet (opcode, 20);
   2499                 imm32 = ThumbExpandImm_C (opcode, APSR_C, carry_out);
   2500 
   2501                 // if BadReg(d) || n == 15 then UNPREDICTABLE;
   2502                 if (BadReg (d) || (n == 15))
   2503                     return false;
   2504 
   2505                 break;
   2506 
   2507             case eEncodingT4:
   2508             {
   2509                 // if Rn == '1111' then SEE ADR;
   2510                 // if Rn == '1101' then SEE ADD (SP plus immediate);
   2511                 // d = UInt(Rd); n = UInt(Rn); setflags = FALSE; imm32 = ZeroExtend(i:imm3:imm8, 32);
   2512                 d = Bits32 (opcode, 11, 8);
   2513                 n = Bits32 (opcode, 19, 16);
   2514                 setflags = false;
   2515                 uint32_t i = Bit32 (opcode, 26);
   2516                 uint32_t imm3 = Bits32 (opcode, 14, 12);
   2517                 uint32_t imm8 = Bits32 (opcode, 7, 0);
   2518                 imm32 = (i << 11) | (imm3 << 8) | imm8;
   2519 
   2520                 // if BadReg(d) then UNPREDICTABLE;
   2521                 if (BadReg (d))
   2522                     return false;
   2523 
   2524                 break;
   2525             }
   2526             default:
   2527                 return false;
   2528         }
   2529 
   2530         uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   2531         if (!success)
   2532             return false;
   2533 
   2534         //(result, carry, overflow) = AddWithCarry(R[n], imm32, '0');
   2535         AddWithCarryResult res = AddWithCarry (Rn, imm32, 0);
   2536 
   2537         RegisterInfo reg_n;
   2538         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, reg_n);
   2539 
   2540         EmulateInstruction::Context context;
   2541         context.type = eContextArithmetic;
   2542         context.SetRegisterPlusOffset (reg_n, imm32);
   2543 
   2544         //R[d] = result;
   2545         //if setflags then
   2546             //APSR.N = result<31>;
   2547             //APSR.Z = IsZeroBit(result);
   2548             //APSR.C = carry;
   2549             //APSR.V = overflow;
   2550         if (!WriteCoreRegOptionalFlags (context, res.result, d, setflags, res.carry_out, res.overflow))
   2551             return false;
   2552 
   2553     }
   2554     return true;
   2555 }
   2556 
   2557 // This instruction adds an immediate value to a register value, and writes the result to the destination
   2558 // register.  It can optionally update the condition flags based on the result.
   2559 bool
   2560 EmulateInstructionARM::EmulateADDImmARM (const uint32_t opcode, const ARMEncoding encoding)
   2561 {
   2562 #if 0
   2563     // ARM pseudo code...
   2564     if ConditionPassed() then
   2565         EncodingSpecificOperations();
   2566         (result, carry, overflow) = AddWithCarry(R[n], imm32, '0');
   2567         if d == 15 then
   2568             ALUWritePC(result); // setflags is always FALSE here
   2569         else
   2570             R[d] = result;
   2571             if setflags then
   2572                 APSR.N = result<31>;
   2573                 APSR.Z = IsZeroBit(result);
   2574                 APSR.C = carry;
   2575                 APSR.V = overflow;
   2576 #endif
   2577 
   2578     bool success = false;
   2579 
   2580     if (ConditionPassed(opcode))
   2581     {
   2582         uint32_t Rd, Rn;
   2583         uint32_t imm32; // the immediate value to be added to the value obtained from Rn
   2584         bool setflags;
   2585         switch (encoding)
   2586         {
   2587         case eEncodingA1:
   2588             Rd = Bits32(opcode, 15, 12);
   2589             Rn = Bits32(opcode, 19, 16);
   2590             setflags = BitIsSet(opcode, 20);
   2591             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   2592             break;
   2593         default:
   2594             return false;
   2595         }
   2596 
   2597         // Read the first operand.
   2598         uint32_t val1 = ReadCoreReg(Rn, &success);
   2599         if (!success)
   2600             return false;
   2601 
   2602         AddWithCarryResult res = AddWithCarry(val1, imm32, 0);
   2603 
   2604         EmulateInstruction::Context context;
   2605         context.type = eContextArithmetic;
   2606         RegisterInfo dwarf_reg;
   2607         GetRegisterInfo (eRegisterKindDWARF, Rn, dwarf_reg);
   2608         context.SetRegisterPlusOffset (dwarf_reg, imm32);
   2609 
   2610         if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   2611             return false;
   2612     }
   2613     return true;
   2614 }
   2615 
   2616 // This instruction adds a register value and an optionally-shifted register value, and writes the result
   2617 // to the destination register. It can optionally update the condition flags based on the result.
   2618 bool
   2619 EmulateInstructionARM::EmulateADDReg (const uint32_t opcode, const ARMEncoding encoding)
   2620 {
   2621 #if 0
   2622     // ARM pseudo code...
   2623     if ConditionPassed() then
   2624         EncodingSpecificOperations();
   2625         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   2626         (result, carry, overflow) = AddWithCarry(R[n], shifted, '0');
   2627         if d == 15 then
   2628             ALUWritePC(result); // setflags is always FALSE here
   2629         else
   2630             R[d] = result;
   2631             if setflags then
   2632                 APSR.N = result<31>;
   2633                 APSR.Z = IsZeroBit(result);
   2634                 APSR.C = carry;
   2635                 APSR.V = overflow;
   2636 #endif
   2637 
   2638     bool success = false;
   2639 
   2640     if (ConditionPassed(opcode))
   2641     {
   2642         uint32_t Rd, Rn, Rm;
   2643         ARM_ShifterType shift_t;
   2644         uint32_t shift_n; // the shift applied to the value read from Rm
   2645         bool setflags;
   2646         switch (encoding)
   2647         {
   2648         case eEncodingT1:
   2649             Rd = Bits32(opcode, 2, 0);
   2650             Rn = Bits32(opcode, 5, 3);
   2651             Rm = Bits32(opcode, 8, 6);
   2652             setflags = !InITBlock();
   2653             shift_t = SRType_LSL;
   2654             shift_n = 0;
   2655             break;
   2656         case eEncodingT2:
   2657             Rd = Rn = Bit32(opcode, 7) << 3 | Bits32(opcode, 2, 0);
   2658             Rm = Bits32(opcode, 6, 3);
   2659             setflags = false;
   2660             shift_t = SRType_LSL;
   2661             shift_n = 0;
   2662             if (Rn == 15 && Rm == 15)
   2663                 return false;
   2664             if (Rd == 15 && InITBlock() && !LastInITBlock())
   2665                 return false;
   2666             break;
   2667         case eEncodingA1:
   2668             Rd = Bits32(opcode, 15, 12);
   2669             Rn = Bits32(opcode, 19, 16);
   2670             Rm = Bits32(opcode, 3, 0);
   2671             setflags = BitIsSet(opcode, 20);
   2672             shift_n = DecodeImmShiftARM(opcode, shift_t);
   2673             break;
   2674         default:
   2675             return false;
   2676         }
   2677 
   2678         // Read the first operand.
   2679         uint32_t val1 = ReadCoreReg(Rn, &success);
   2680         if (!success)
   2681             return false;
   2682 
   2683         // Read the second operand.
   2684         uint32_t val2 = ReadCoreReg(Rm, &success);
   2685         if (!success)
   2686             return false;
   2687 
   2688         uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   2689         if (!success)
   2690             return false;
   2691         AddWithCarryResult res = AddWithCarry(val1, shifted, 0);
   2692 
   2693         EmulateInstruction::Context context;
   2694         context.type = eContextArithmetic;
   2695         RegisterInfo op1_reg;
   2696         RegisterInfo op2_reg;
   2697         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rn, op1_reg);
   2698         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rm, op2_reg);
   2699         context.SetRegisterRegisterOperands (op1_reg, op2_reg);
   2700 
   2701         if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   2702             return false;
   2703     }
   2704     return true;
   2705 }
   2706 
   2707 // Compare Negative (immediate) adds a register value and an immediate value.
   2708 // It updates the condition flags based on the result, and discards the result.
   2709 bool
   2710 EmulateInstructionARM::EmulateCMNImm (const uint32_t opcode, const ARMEncoding encoding)
   2711 {
   2712 #if 0
   2713     // ARM pseudo code...
   2714     if ConditionPassed() then
   2715         EncodingSpecificOperations();
   2716         (result, carry, overflow) = AddWithCarry(R[n], imm32, '0');
   2717         APSR.N = result<31>;
   2718         APSR.Z = IsZeroBit(result);
   2719         APSR.C = carry;
   2720         APSR.V = overflow;
   2721 #endif
   2722 
   2723     bool success = false;
   2724 
   2725     uint32_t Rn; // the first operand
   2726     uint32_t imm32; // the immediate value to be compared with
   2727     switch (encoding) {
   2728     case eEncodingT1:
   2729         Rn = Bits32(opcode, 19, 16);
   2730         imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   2731         if (Rn == 15)
   2732             return false;
   2733         break;
   2734     case eEncodingA1:
   2735         Rn = Bits32(opcode, 19, 16);
   2736         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   2737         break;
   2738     default:
   2739         return false;
   2740     }
   2741     // Read the register value from the operand register Rn.
   2742     uint32_t reg_val = ReadCoreReg(Rn, &success);
   2743     if (!success)
   2744         return false;
   2745 
   2746     AddWithCarryResult res = AddWithCarry(reg_val, imm32, 0);
   2747 
   2748     EmulateInstruction::Context context;
   2749     context.type = EmulateInstruction::eContextImmediate;
   2750     context.SetNoArgs ();
   2751     if (!WriteFlags(context, res.result, res.carry_out, res.overflow))
   2752         return false;
   2753 
   2754     return true;
   2755 }
   2756 
   2757 // Compare Negative (register) adds a register value and an optionally-shifted register value.
   2758 // It updates the condition flags based on the result, and discards the result.
   2759 bool
   2760 EmulateInstructionARM::EmulateCMNReg (const uint32_t opcode, const ARMEncoding encoding)
   2761 {
   2762 #if 0
   2763     // ARM pseudo code...
   2764     if ConditionPassed() then
   2765         EncodingSpecificOperations();
   2766         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   2767         (result, carry, overflow) = AddWithCarry(R[n], shifted, '0');
   2768         APSR.N = result<31>;
   2769         APSR.Z = IsZeroBit(result);
   2770         APSR.C = carry;
   2771         APSR.V = overflow;
   2772 #endif
   2773 
   2774     bool success = false;
   2775 
   2776     uint32_t Rn; // the first operand
   2777     uint32_t Rm; // the second operand
   2778     ARM_ShifterType shift_t;
   2779     uint32_t shift_n; // the shift applied to the value read from Rm
   2780     switch (encoding) {
   2781     case eEncodingT1:
   2782         Rn = Bits32(opcode, 2, 0);
   2783         Rm = Bits32(opcode, 5, 3);
   2784         shift_t = SRType_LSL;
   2785         shift_n = 0;
   2786         break;
   2787     case eEncodingT2:
   2788         Rn = Bits32(opcode, 19, 16);
   2789         Rm = Bits32(opcode, 3, 0);
   2790         shift_n = DecodeImmShiftThumb(opcode, shift_t);
   2791         // if n == 15 || BadReg(m) then UNPREDICTABLE;
   2792         if (Rn == 15 || BadReg(Rm))
   2793             return false;
   2794         break;
   2795     case eEncodingA1:
   2796         Rn = Bits32(opcode, 19, 16);
   2797         Rm = Bits32(opcode, 3, 0);
   2798         shift_n = DecodeImmShiftARM(opcode, shift_t);
   2799         break;
   2800     default:
   2801         return false;
   2802     }
   2803     // Read the register value from register Rn.
   2804     uint32_t val1 = ReadCoreReg(Rn, &success);
   2805     if (!success)
   2806         return false;
   2807 
   2808     // Read the register value from register Rm.
   2809     uint32_t val2 = ReadCoreReg(Rm, &success);
   2810     if (!success)
   2811         return false;
   2812 
   2813     uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   2814     if (!success)
   2815         return false;
   2816     AddWithCarryResult res = AddWithCarry(val1, shifted, 0);
   2817 
   2818     EmulateInstruction::Context context;
   2819     context.type = EmulateInstruction::eContextImmediate;
   2820     context.SetNoArgs();
   2821     if (!WriteFlags(context, res.result, res.carry_out, res.overflow))
   2822         return false;
   2823 
   2824     return true;
   2825 }
   2826 
   2827 // Compare (immediate) subtracts an immediate value from a register value.
   2828 // It updates the condition flags based on the result, and discards the result.
   2829 bool
   2830 EmulateInstructionARM::EmulateCMPImm (const uint32_t opcode, const ARMEncoding encoding)
   2831 {
   2832 #if 0
   2833     // ARM pseudo code...
   2834     if ConditionPassed() then
   2835         EncodingSpecificOperations();
   2836         (result, carry, overflow) = AddWithCarry(R[n], NOT(imm32), '1');
   2837         APSR.N = result<31>;
   2838         APSR.Z = IsZeroBit(result);
   2839         APSR.C = carry;
   2840         APSR.V = overflow;
   2841 #endif
   2842 
   2843     bool success = false;
   2844 
   2845     uint32_t Rn; // the first operand
   2846     uint32_t imm32; // the immediate value to be compared with
   2847     switch (encoding) {
   2848     case eEncodingT1:
   2849         Rn = Bits32(opcode, 10, 8);
   2850         imm32 = Bits32(opcode, 7, 0);
   2851         break;
   2852     case eEncodingT2:
   2853         Rn = Bits32(opcode, 19, 16);
   2854         imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   2855         if (Rn == 15)
   2856             return false;
   2857         break;
   2858     case eEncodingA1:
   2859         Rn = Bits32(opcode, 19, 16);
   2860         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   2861         break;
   2862     default:
   2863         return false;
   2864     }
   2865     // Read the register value from the operand register Rn.
   2866     uint32_t reg_val = ReadCoreReg(Rn, &success);
   2867     if (!success)
   2868         return false;
   2869 
   2870     AddWithCarryResult res = AddWithCarry(reg_val, ~imm32, 1);
   2871 
   2872     EmulateInstruction::Context context;
   2873     context.type = EmulateInstruction::eContextImmediate;
   2874     context.SetNoArgs ();
   2875     if (!WriteFlags(context, res.result, res.carry_out, res.overflow))
   2876         return false;
   2877 
   2878     return true;
   2879 }
   2880 
   2881 // Compare (register) subtracts an optionally-shifted register value from a register value.
   2882 // It updates the condition flags based on the result, and discards the result.
   2883 bool
   2884 EmulateInstructionARM::EmulateCMPReg (const uint32_t opcode, const ARMEncoding encoding)
   2885 {
   2886 #if 0
   2887     // ARM pseudo code...
   2888     if ConditionPassed() then
   2889         EncodingSpecificOperations();
   2890         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   2891         (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), '1');
   2892         APSR.N = result<31>;
   2893         APSR.Z = IsZeroBit(result);
   2894         APSR.C = carry;
   2895         APSR.V = overflow;
   2896 #endif
   2897 
   2898     bool success = false;
   2899 
   2900     uint32_t Rn; // the first operand
   2901     uint32_t Rm; // the second operand
   2902     ARM_ShifterType shift_t;
   2903     uint32_t shift_n; // the shift applied to the value read from Rm
   2904     switch (encoding) {
   2905     case eEncodingT1:
   2906         Rn = Bits32(opcode, 2, 0);
   2907         Rm = Bits32(opcode, 5, 3);
   2908         shift_t = SRType_LSL;
   2909         shift_n = 0;
   2910         break;
   2911     case eEncodingT2:
   2912         Rn = Bit32(opcode, 7) << 3 | Bits32(opcode, 2, 0);
   2913         Rm = Bits32(opcode, 6, 3);
   2914         shift_t = SRType_LSL;
   2915         shift_n = 0;
   2916         if (Rn < 8 && Rm < 8)
   2917             return false;
   2918         if (Rn == 15 || Rm == 15)
   2919             return false;
   2920         break;
   2921     case eEncodingA1:
   2922         Rn = Bits32(opcode, 19, 16);
   2923         Rm = Bits32(opcode, 3, 0);
   2924         shift_n = DecodeImmShiftARM(opcode, shift_t);
   2925         break;
   2926     default:
   2927         return false;
   2928     }
   2929     // Read the register value from register Rn.
   2930     uint32_t val1 = ReadCoreReg(Rn, &success);
   2931     if (!success)
   2932         return false;
   2933 
   2934     // Read the register value from register Rm.
   2935     uint32_t val2 = ReadCoreReg(Rm, &success);
   2936     if (!success)
   2937         return false;
   2938 
   2939     uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   2940     if (!success)
   2941         return false;
   2942     AddWithCarryResult res = AddWithCarry(val1, ~shifted, 1);
   2943 
   2944     EmulateInstruction::Context context;
   2945     context.type = EmulateInstruction::eContextImmediate;
   2946     context.SetNoArgs();
   2947     if (!WriteFlags(context, res.result, res.carry_out, res.overflow))
   2948         return false;
   2949 
   2950     return true;
   2951 }
   2952 
   2953 // Arithmetic Shift Right (immediate) shifts a register value right by an immediate number of bits,
   2954 // shifting in copies of its sign bit, and writes the result to the destination register.  It can
   2955 // optionally update the condition flags based on the result.
   2956 bool
   2957 EmulateInstructionARM::EmulateASRImm (const uint32_t opcode, const ARMEncoding encoding)
   2958 {
   2959 #if 0
   2960     // ARM pseudo code...
   2961     if ConditionPassed() then
   2962         EncodingSpecificOperations();
   2963         (result, carry) = Shift_C(R[m], SRType_ASR, shift_n, APSR.C);
   2964         if d == 15 then         // Can only occur for ARM encoding
   2965             ALUWritePC(result); // setflags is always FALSE here
   2966         else
   2967             R[d] = result;
   2968             if setflags then
   2969                 APSR.N = result<31>;
   2970                 APSR.Z = IsZeroBit(result);
   2971                 APSR.C = carry;
   2972                 // APSR.V unchanged
   2973 #endif
   2974 
   2975     return EmulateShiftImm (opcode, encoding, SRType_ASR);
   2976 }
   2977 
   2978 // Arithmetic Shift Right (register) shifts a register value right by a variable number of bits,
   2979 // shifting in copies of its sign bit, and writes the result to the destination register.
   2980 // The variable number of bits is read from the bottom byte of a register. It can optionally update
   2981 // the condition flags based on the result.
   2982 bool
   2983 EmulateInstructionARM::EmulateASRReg (const uint32_t opcode, const ARMEncoding encoding)
   2984 {
   2985 #if 0
   2986     // ARM pseudo code...
   2987     if ConditionPassed() then
   2988         EncodingSpecificOperations();
   2989         shift_n = UInt(R[m]<7:0>);
   2990         (result, carry) = Shift_C(R[m], SRType_ASR, shift_n, APSR.C);
   2991         R[d] = result;
   2992         if setflags then
   2993             APSR.N = result<31>;
   2994             APSR.Z = IsZeroBit(result);
   2995             APSR.C = carry;
   2996             // APSR.V unchanged
   2997 #endif
   2998 
   2999     return EmulateShiftReg (opcode, encoding, SRType_ASR);
   3000 }
   3001 
   3002 // Logical Shift Left (immediate) shifts a register value left by an immediate number of bits,
   3003 // shifting in zeros, and writes the result to the destination register.  It can optionally
   3004 // update the condition flags based on the result.
   3005 bool
   3006 EmulateInstructionARM::EmulateLSLImm (const uint32_t opcode, const ARMEncoding encoding)
   3007 {
   3008 #if 0
   3009     // ARM pseudo code...
   3010     if ConditionPassed() then
   3011         EncodingSpecificOperations();
   3012         (result, carry) = Shift_C(R[m], SRType_LSL, shift_n, APSR.C);
   3013         if d == 15 then         // Can only occur for ARM encoding
   3014             ALUWritePC(result); // setflags is always FALSE here
   3015         else
   3016             R[d] = result;
   3017             if setflags then
   3018                 APSR.N = result<31>;
   3019                 APSR.Z = IsZeroBit(result);
   3020                 APSR.C = carry;
   3021                 // APSR.V unchanged
   3022 #endif
   3023 
   3024     return EmulateShiftImm (opcode, encoding, SRType_LSL);
   3025 }
   3026 
   3027 // Logical Shift Left (register) shifts a register value left by a variable number of bits,
   3028 // shifting in zeros, and writes the result to the destination register.  The variable number
   3029 // of bits is read from the bottom byte of a register. It can optionally update the condition
   3030 // flags based on the result.
   3031 bool
   3032 EmulateInstructionARM::EmulateLSLReg (const uint32_t opcode, const ARMEncoding encoding)
   3033 {
   3034 #if 0
   3035     // ARM pseudo code...
   3036     if ConditionPassed() then
   3037         EncodingSpecificOperations();
   3038         shift_n = UInt(R[m]<7:0>);
   3039         (result, carry) = Shift_C(R[m], SRType_LSL, shift_n, APSR.C);
   3040         R[d] = result;
   3041         if setflags then
   3042             APSR.N = result<31>;
   3043             APSR.Z = IsZeroBit(result);
   3044             APSR.C = carry;
   3045             // APSR.V unchanged
   3046 #endif
   3047 
   3048     return EmulateShiftReg (opcode, encoding, SRType_LSL);
   3049 }
   3050 
   3051 // Logical Shift Right (immediate) shifts a register value right by an immediate number of bits,
   3052 // shifting in zeros, and writes the result to the destination register.  It can optionally
   3053 // update the condition flags based on the result.
   3054 bool
   3055 EmulateInstructionARM::EmulateLSRImm (const uint32_t opcode, const ARMEncoding encoding)
   3056 {
   3057 #if 0
   3058     // ARM pseudo code...
   3059     if ConditionPassed() then
   3060         EncodingSpecificOperations();
   3061         (result, carry) = Shift_C(R[m], SRType_LSR, shift_n, APSR.C);
   3062         if d == 15 then         // Can only occur for ARM encoding
   3063             ALUWritePC(result); // setflags is always FALSE here
   3064         else
   3065             R[d] = result;
   3066             if setflags then
   3067                 APSR.N = result<31>;
   3068                 APSR.Z = IsZeroBit(result);
   3069                 APSR.C = carry;
   3070                 // APSR.V unchanged
   3071 #endif
   3072 
   3073     return EmulateShiftImm (opcode, encoding, SRType_LSR);
   3074 }
   3075 
   3076 // Logical Shift Right (register) shifts a register value right by a variable number of bits,
   3077 // shifting in zeros, and writes the result to the destination register.  The variable number
   3078 // of bits is read from the bottom byte of a register. It can optionally update the condition
   3079 // flags based on the result.
   3080 bool
   3081 EmulateInstructionARM::EmulateLSRReg (const uint32_t opcode, const ARMEncoding encoding)
   3082 {
   3083 #if 0
   3084     // ARM pseudo code...
   3085     if ConditionPassed() then
   3086         EncodingSpecificOperations();
   3087         shift_n = UInt(R[m]<7:0>);
   3088         (result, carry) = Shift_C(R[m], SRType_LSR, shift_n, APSR.C);
   3089         R[d] = result;
   3090         if setflags then
   3091             APSR.N = result<31>;
   3092             APSR.Z = IsZeroBit(result);
   3093             APSR.C = carry;
   3094             // APSR.V unchanged
   3095 #endif
   3096 
   3097     return EmulateShiftReg (opcode, encoding, SRType_LSR);
   3098 }
   3099 
   3100 // Rotate Right (immediate) provides the value of the contents of a register rotated by a constant value.
   3101 // The bits that are rotated off the right end are inserted into the vacated bit positions on the left.
   3102 // It can optionally update the condition flags based on the result.
   3103 bool
   3104 EmulateInstructionARM::EmulateRORImm (const uint32_t opcode, const ARMEncoding encoding)
   3105 {
   3106 #if 0
   3107     // ARM pseudo code...
   3108     if ConditionPassed() then
   3109         EncodingSpecificOperations();
   3110         (result, carry) = Shift_C(R[m], SRType_ROR, shift_n, APSR.C);
   3111         if d == 15 then         // Can only occur for ARM encoding
   3112             ALUWritePC(result); // setflags is always FALSE here
   3113         else
   3114             R[d] = result;
   3115             if setflags then
   3116                 APSR.N = result<31>;
   3117                 APSR.Z = IsZeroBit(result);
   3118                 APSR.C = carry;
   3119                 // APSR.V unchanged
   3120 #endif
   3121 
   3122     return EmulateShiftImm (opcode, encoding, SRType_ROR);
   3123 }
   3124 
   3125 // Rotate Right (register) provides the value of the contents of a register rotated by a variable number of bits.
   3126 // The bits that are rotated off the right end are inserted into the vacated bit positions on the left.
   3127 // The variable number of bits is read from the bottom byte of a register. It can optionally update the condition
   3128 // flags based on the result.
   3129 bool
   3130 EmulateInstructionARM::EmulateRORReg (const uint32_t opcode, const ARMEncoding encoding)
   3131 {
   3132 #if 0
   3133     // ARM pseudo code...
   3134     if ConditionPassed() then
   3135         EncodingSpecificOperations();
   3136         shift_n = UInt(R[m]<7:0>);
   3137         (result, carry) = Shift_C(R[m], SRType_ROR, shift_n, APSR.C);
   3138         R[d] = result;
   3139         if setflags then
   3140             APSR.N = result<31>;
   3141             APSR.Z = IsZeroBit(result);
   3142             APSR.C = carry;
   3143             // APSR.V unchanged
   3144 #endif
   3145 
   3146     return EmulateShiftReg (opcode, encoding, SRType_ROR);
   3147 }
   3148 
   3149 // Rotate Right with Extend provides the value of the contents of a register shifted right by one place,
   3150 // with the carry flag shifted into bit [31].
   3151 //
   3152 // RRX can optionally update the condition flags based on the result.
   3153 // In that case, bit [0] is shifted into the carry flag.
   3154 bool
   3155 EmulateInstructionARM::EmulateRRX (const uint32_t opcode, const ARMEncoding encoding)
   3156 {
   3157 #if 0
   3158     // ARM pseudo code...
   3159     if ConditionPassed() then
   3160         EncodingSpecificOperations();
   3161         (result, carry) = Shift_C(R[m], SRType_RRX, 1, APSR.C);
   3162         if d == 15 then         // Can only occur for ARM encoding
   3163             ALUWritePC(result); // setflags is always FALSE here
   3164         else
   3165             R[d] = result;
   3166             if setflags then
   3167                 APSR.N = result<31>;
   3168                 APSR.Z = IsZeroBit(result);
   3169                 APSR.C = carry;
   3170                 // APSR.V unchanged
   3171 #endif
   3172 
   3173     return EmulateShiftImm (opcode, encoding, SRType_RRX);
   3174 }
   3175 
   3176 bool
   3177 EmulateInstructionARM::EmulateShiftImm (const uint32_t opcode, const ARMEncoding encoding, ARM_ShifterType shift_type)
   3178 {
   3179 //    assert(shift_type == SRType_ASR
   3180 //           || shift_type == SRType_LSL
   3181 //           || shift_type == SRType_LSR
   3182 //           || shift_type == SRType_ROR
   3183 //           || shift_type == SRType_RRX);
   3184 
   3185     bool success = false;
   3186 
   3187     if (ConditionPassed(opcode))
   3188     {
   3189         uint32_t Rd;    // the destination register
   3190         uint32_t Rm;    // the first operand register
   3191         uint32_t imm5;  // encoding for the shift amount
   3192         uint32_t carry; // the carry bit after the shift operation
   3193         bool setflags;
   3194 
   3195         // Special case handling!
   3196         // A8.6.139 ROR (immediate) -- Encoding T1
   3197         ARMEncoding use_encoding = encoding;
   3198         if (shift_type == SRType_ROR && use_encoding == eEncodingT1)
   3199         {
   3200             // Morph the T1 encoding from the ARM Architecture Manual into T2 encoding to
   3201             // have the same decoding of bit fields as the other Thumb2 shift operations.
   3202             use_encoding = eEncodingT2;
   3203         }
   3204 
   3205         switch (use_encoding) {
   3206         case eEncodingT1:
   3207             // Due to the above special case handling!
   3208             if (shift_type == SRType_ROR)
   3209                 return false;
   3210 
   3211             Rd = Bits32(opcode, 2, 0);
   3212             Rm = Bits32(opcode, 5, 3);
   3213             setflags = !InITBlock();
   3214             imm5 = Bits32(opcode, 10, 6);
   3215             break;
   3216         case eEncodingT2:
   3217             // A8.6.141 RRX
   3218             // There's no imm form of RRX instructions.
   3219             if (shift_type == SRType_RRX)
   3220                 return false;
   3221 
   3222             Rd = Bits32(opcode, 11, 8);
   3223             Rm = Bits32(opcode, 3, 0);
   3224             setflags = BitIsSet(opcode, 20);
   3225             imm5 = Bits32(opcode, 14, 12) << 2 | Bits32(opcode, 7, 6);
   3226             if (BadReg(Rd) || BadReg(Rm))
   3227                 return false;
   3228             break;
   3229         case eEncodingA1:
   3230             Rd = Bits32(opcode, 15, 12);
   3231             Rm = Bits32(opcode, 3, 0);
   3232             setflags = BitIsSet(opcode, 20);
   3233             imm5 = Bits32(opcode, 11, 7);
   3234             break;
   3235         default:
   3236             return false;
   3237         }
   3238 
   3239         // A8.6.139 ROR (immediate)
   3240         if (shift_type == SRType_ROR && imm5 == 0)
   3241             shift_type = SRType_RRX;
   3242 
   3243         // Get the first operand.
   3244         uint32_t value = ReadCoreReg (Rm, &success);
   3245         if (!success)
   3246             return false;
   3247 
   3248         // Decode the shift amount if not RRX.
   3249         uint32_t amt = (shift_type == SRType_RRX ? 1 : DecodeImmShift(shift_type, imm5));
   3250 
   3251         uint32_t result = Shift_C(value, shift_type, amt, APSR_C, carry, &success);
   3252         if (!success)
   3253             return false;
   3254 
   3255         // The context specifies that an immediate is to be moved into Rd.
   3256         EmulateInstruction::Context context;
   3257         context.type = EmulateInstruction::eContextImmediate;
   3258         context.SetNoArgs ();
   3259 
   3260         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   3261             return false;
   3262     }
   3263     return true;
   3264 }
   3265 
   3266 bool
   3267 EmulateInstructionARM::EmulateShiftReg (const uint32_t opcode, const ARMEncoding encoding, ARM_ShifterType shift_type)
   3268 {
   3269     // assert(shift_type == SRType_ASR
   3270     //        || shift_type == SRType_LSL
   3271     //        || shift_type == SRType_LSR
   3272     //        || shift_type == SRType_ROR);
   3273 
   3274     bool success = false;
   3275 
   3276     if (ConditionPassed(opcode))
   3277     {
   3278         uint32_t Rd;    // the destination register
   3279         uint32_t Rn;    // the first operand register
   3280         uint32_t Rm;    // the register whose bottom byte contains the amount to shift by
   3281         uint32_t carry; // the carry bit after the shift operation
   3282         bool setflags;
   3283         switch (encoding) {
   3284         case eEncodingT1:
   3285             Rd = Bits32(opcode, 2, 0);
   3286             Rn = Rd;
   3287             Rm = Bits32(opcode, 5, 3);
   3288             setflags = !InITBlock();
   3289             break;
   3290         case eEncodingT2:
   3291             Rd = Bits32(opcode, 11, 8);
   3292             Rn = Bits32(opcode, 19, 16);
   3293             Rm = Bits32(opcode, 3, 0);
   3294             setflags = BitIsSet(opcode, 20);
   3295             if (BadReg(Rd) || BadReg(Rn) || BadReg(Rm))
   3296                 return false;
   3297             break;
   3298         case eEncodingA1:
   3299             Rd = Bits32(opcode, 15, 12);
   3300             Rn = Bits32(opcode, 3, 0);
   3301             Rm = Bits32(opcode, 11, 8);
   3302             setflags = BitIsSet(opcode, 20);
   3303             if (Rd == 15 || Rn == 15 || Rm == 15)
   3304                 return false;
   3305             break;
   3306         default:
   3307             return false;
   3308         }
   3309 
   3310         // Get the first operand.
   3311         uint32_t value = ReadCoreReg (Rn, &success);
   3312         if (!success)
   3313             return false;
   3314         // Get the Rm register content.
   3315         uint32_t val = ReadCoreReg (Rm, &success);
   3316         if (!success)
   3317             return false;
   3318 
   3319         // Get the shift amount.
   3320         uint32_t amt = Bits32(val, 7, 0);
   3321 
   3322         uint32_t result = Shift_C(value, shift_type, amt, APSR_C, carry, &success);
   3323         if (!success)
   3324             return false;
   3325 
   3326         // The context specifies that an immediate is to be moved into Rd.
   3327         EmulateInstruction::Context context;
   3328         context.type = EmulateInstruction::eContextImmediate;
   3329         context.SetNoArgs ();
   3330 
   3331         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   3332             return false;
   3333     }
   3334     return true;
   3335 }
   3336 
   3337 // LDM loads multiple registers from consecutive memory locations, using an
   3338 // address from a base register.  Optionally the address just above the highest of those locations
   3339 // can be written back to the base register.
   3340 bool
   3341 EmulateInstructionARM::EmulateLDM (const uint32_t opcode, const ARMEncoding encoding)
   3342 {
   3343 #if 0
   3344     // ARM pseudo code...
   3345     if ConditionPassed()
   3346         EncodingSpecificOperations(); NullCheckIfThumbEE (n);
   3347         address = R[n];
   3348 
   3349         for i = 0 to 14
   3350             if registers<i> == '1' then
   3351                 R[i] = MemA[address, 4]; address = address + 4;
   3352         if registers<15> == '1' then
   3353             LoadWritePC (MemA[address, 4]);
   3354 
   3355         if wback && registers<n> == '0' then R[n] = R[n] + 4 * BitCount (registers);
   3356         if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN; // Only possible for encoding A1
   3357 
   3358 #endif
   3359 
   3360     bool success = false;
   3361     bool conditional = false;
   3362     if (ConditionPassed(opcode, &conditional))
   3363     {
   3364         uint32_t n;
   3365         uint32_t registers = 0;
   3366         bool wback;
   3367         const uint32_t addr_byte_size = GetAddressByteSize();
   3368         switch (encoding)
   3369         {
   3370             case eEncodingT1:
   3371                 // n = UInt(Rn); registers = '00000000':register_list; wback = (registers<n> == '0');
   3372                 n = Bits32 (opcode, 10, 8);
   3373                 registers = Bits32 (opcode, 7, 0);
   3374                 registers = registers & 0x00ff;  // Make sure the top 8 bits are zeros.
   3375                 wback = BitIsClear (registers, n);
   3376                 // if BitCount(registers) < 1 then UNPREDICTABLE;
   3377                 if (BitCount(registers) < 1)
   3378                     return false;
   3379                 break;
   3380             case eEncodingT2:
   3381                 // if W == '1' && Rn == '1101' then SEE POP;
   3382                 // n = UInt(Rn); registers = P:M:'0':register_list; wback = (W == '1');
   3383                 n = Bits32 (opcode, 19, 16);
   3384                 registers = Bits32 (opcode, 15, 0);
   3385                 registers = registers & 0xdfff; // Make sure bit 13 is zero.
   3386                 wback = BitIsSet (opcode, 21);
   3387 
   3388                 // if n == 15 || BitCount(registers) < 2 || (P == '1' && M == '1') then UNPREDICTABLE;
   3389                 if ((n == 15)
   3390                     || (BitCount (registers) < 2)
   3391                     || (BitIsSet (opcode, 14) && BitIsSet (opcode, 15)))
   3392                     return false;
   3393 
   3394                 // if registers<15> == '1' && InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   3395                 if (BitIsSet (registers, 15) && InITBlock() && !LastInITBlock())
   3396                     return false;
   3397 
   3398                 // if wback && registers<n> == '1' then UNPREDICTABLE;
   3399                 if (wback
   3400                     && BitIsSet (registers, n))
   3401                     return false;
   3402                 break;
   3403 
   3404             case eEncodingA1:
   3405                 n = Bits32 (opcode, 19, 16);
   3406                 registers = Bits32 (opcode, 15, 0);
   3407                 wback = BitIsSet (opcode, 21);
   3408                 if ((n == 15)
   3409                     || (BitCount (registers) < 1))
   3410                     return false;
   3411                 break;
   3412             default:
   3413                 return false;
   3414         }
   3415 
   3416         int32_t offset = 0;
   3417         const addr_t base_address = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   3418         if (!success)
   3419             return false;
   3420 
   3421         EmulateInstruction::Context context;
   3422         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3423         RegisterInfo dwarf_reg;
   3424         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, dwarf_reg);
   3425         context.SetRegisterPlusOffset (dwarf_reg, offset);
   3426 
   3427         for (int i = 0; i < 14; ++i)
   3428         {
   3429             if (BitIsSet (registers, i))
   3430             {
   3431                 context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3432                 context.SetRegisterPlusOffset (dwarf_reg, offset);
   3433                 if (wback && (n == 13)) // Pop Instruction
   3434                 {
   3435                     if (conditional)
   3436                         context.type = EmulateInstruction::eContextRegisterLoad;
   3437                     else
   3438                         context.type = EmulateInstruction::eContextPopRegisterOffStack;
   3439                 }
   3440 
   3441                 // R[i] = MemA [address, 4]; address = address + 4;
   3442                 uint32_t data = MemARead (context, base_address + offset, addr_byte_size, 0, &success);
   3443                 if (!success)
   3444                     return false;
   3445 
   3446                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + i, data))
   3447                     return false;
   3448 
   3449                 offset += addr_byte_size;
   3450             }
   3451         }
   3452 
   3453         if (BitIsSet (registers, 15))
   3454         {
   3455             //LoadWritePC (MemA [address, 4]);
   3456             context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3457             context.SetRegisterPlusOffset (dwarf_reg, offset);
   3458             uint32_t data = MemARead (context, base_address + offset, addr_byte_size, 0, &success);
   3459             if (!success)
   3460                 return false;
   3461             // In ARMv5T and above, this is an interworking branch.
   3462             if (!LoadWritePC(context, data))
   3463                 return false;
   3464         }
   3465 
   3466         if (wback && BitIsClear (registers, n))
   3467         {
   3468             // R[n] = R[n] + 4 * BitCount (registers)
   3469             int32_t offset = addr_byte_size * BitCount (registers);
   3470             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   3471             context.SetRegisterPlusOffset (dwarf_reg, offset);
   3472 
   3473             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, base_address + offset))
   3474                 return false;
   3475         }
   3476         if (wback && BitIsSet (registers, n))
   3477             // R[n] bits(32) UNKNOWN;
   3478             return WriteBits32Unknown (n);
   3479     }
   3480     return true;
   3481 }
   3482 
   3483 // LDMDA loads multiple registers from consecutive memory locations using an address from a base register.
   3484 // The consecutive memory locations end at this address and the address just below the lowest of those locations
   3485 // can optionally be written back to the base register.
   3486 bool
   3487 EmulateInstructionARM::EmulateLDMDA (const uint32_t opcode, const ARMEncoding encoding)
   3488 {
   3489 #if 0
   3490     // ARM pseudo code...
   3491     if ConditionPassed() then
   3492         EncodingSpecificOperations();
   3493         address = R[n] - 4*BitCount(registers) + 4;
   3494 
   3495         for i = 0 to 14
   3496             if registers<i> == '1' then
   3497                   R[i] = MemA[address,4]; address = address + 4;
   3498 
   3499         if registers<15> == '1' then
   3500             LoadWritePC(MemA[address,4]);
   3501 
   3502         if wback && registers<n> == '0' then R[n] = R[n] - 4*BitCount(registers);
   3503         if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN;
   3504 #endif
   3505 
   3506     bool success = false;
   3507 
   3508     if (ConditionPassed(opcode))
   3509     {
   3510         uint32_t n;
   3511         uint32_t registers = 0;
   3512         bool wback;
   3513         const uint32_t addr_byte_size = GetAddressByteSize();
   3514 
   3515         // EncodingSpecificOperations();
   3516         switch (encoding)
   3517         {
   3518             case eEncodingA1:
   3519                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   3520                 n = Bits32 (opcode, 19, 16);
   3521                 registers = Bits32 (opcode, 15, 0);
   3522                 wback = BitIsSet (opcode, 21);
   3523 
   3524                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   3525                 if ((n == 15) || (BitCount (registers) < 1))
   3526                     return false;
   3527 
   3528                 break;
   3529 
   3530             default:
   3531                 return false;
   3532         }
   3533         // address = R[n] - 4*BitCount(registers) + 4;
   3534 
   3535         int32_t offset = 0;
   3536         addr_t Rn = ReadCoreReg (n, &success);
   3537 
   3538         if (!success)
   3539             return false;
   3540 
   3541         addr_t address = Rn - (addr_byte_size * BitCount (registers)) + addr_byte_size;
   3542 
   3543         EmulateInstruction::Context context;
   3544         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3545         RegisterInfo dwarf_reg;
   3546         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, dwarf_reg);
   3547         context.SetRegisterPlusOffset (dwarf_reg, offset);
   3548 
   3549         // for i = 0 to 14
   3550         for (int i = 0; i < 14; ++i)
   3551         {
   3552             // if registers<i> == '1' then
   3553             if (BitIsSet (registers, i))
   3554             {
   3555                   // R[i] = MemA[address,4]; address = address + 4;
   3556                   context.SetRegisterPlusOffset (dwarf_reg, Rn - (address + offset));
   3557                   uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3558                   if (!success)
   3559                       return false;
   3560                   if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + i, data))
   3561                       return false;
   3562                   offset += addr_byte_size;
   3563             }
   3564         }
   3565 
   3566         // if registers<15> == '1' then
   3567         //     LoadWritePC(MemA[address,4]);
   3568         if (BitIsSet (registers, 15))
   3569         {
   3570             context.SetRegisterPlusOffset (dwarf_reg, offset);
   3571             uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3572             if (!success)
   3573                 return false;
   3574             // In ARMv5T and above, this is an interworking branch.
   3575             if (!LoadWritePC(context, data))
   3576                 return false;
   3577         }
   3578 
   3579         // if wback && registers<n> == '0' then R[n] = R[n] - 4*BitCount(registers);
   3580         if (wback && BitIsClear (registers, n))
   3581         {
   3582             if (!success)
   3583                 return false;
   3584 
   3585             offset = (addr_byte_size * BitCount (registers)) * -1;
   3586             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   3587             context.SetImmediateSigned (offset);
   3588             addr_t addr = Rn + offset;
   3589             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, addr))
   3590                 return false;
   3591         }
   3592 
   3593         // if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN;
   3594         if (wback && BitIsSet (registers, n))
   3595             return WriteBits32Unknown (n);
   3596     }
   3597     return true;
   3598 }
   3599 
   3600 // LDMDB loads multiple registers from consecutive memory locations using an address from a base register.  The
   3601 // consecutive memory lcoations end just below this address, and the address of the lowest of those locations can
   3602 // be optionally written back to the base register.
   3603 bool
   3604 EmulateInstructionARM::EmulateLDMDB (const uint32_t opcode, const ARMEncoding encoding)
   3605 {
   3606 #if 0
   3607     // ARM pseudo code...
   3608     if ConditionPassed() then
   3609         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   3610         address = R[n] - 4*BitCount(registers);
   3611 
   3612         for i = 0 to 14
   3613             if registers<i> == '1' then
   3614                   R[i] = MemA[address,4]; address = address + 4;
   3615         if registers<15> == '1' then
   3616                   LoadWritePC(MemA[address,4]);
   3617 
   3618         if wback && registers<n> == '0' then R[n] = R[n] - 4*BitCount(registers);
   3619         if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN; // Only possible for encoding A1
   3620 #endif
   3621 
   3622     bool success = false;
   3623 
   3624     if (ConditionPassed(opcode))
   3625     {
   3626         uint32_t n;
   3627         uint32_t registers = 0;
   3628         bool wback;
   3629         const uint32_t addr_byte_size = GetAddressByteSize();
   3630         switch (encoding)
   3631         {
   3632             case eEncodingT1:
   3633                 // n = UInt(Rn); registers = P:M:'0':register_list; wback = (W == '1');
   3634                 n = Bits32 (opcode, 19, 16);
   3635                 registers = Bits32 (opcode, 15, 0);
   3636                 registers = registers & 0xdfff;  // Make sure bit 13 is a zero.
   3637                 wback = BitIsSet (opcode, 21);
   3638 
   3639                 // if n == 15 || BitCount(registers) < 2 || (P == '1' && M == '1') then UNPREDICTABLE;
   3640                 if ((n == 15)
   3641                     || (BitCount (registers) < 2)
   3642                     || (BitIsSet (opcode, 14) && BitIsSet (opcode, 15)))
   3643                     return false;
   3644 
   3645                 // if registers<15> == '1' && InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   3646                 if (BitIsSet (registers, 15) && InITBlock() && !LastInITBlock())
   3647                     return false;
   3648 
   3649                 // if wback && registers<n> == '1' then UNPREDICTABLE;
   3650                 if (wback && BitIsSet (registers, n))
   3651                     return false;
   3652 
   3653                 break;
   3654 
   3655             case eEncodingA1:
   3656                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   3657                 n = Bits32 (opcode, 19, 16);
   3658                 registers = Bits32 (opcode, 15, 0);
   3659                 wback = BitIsSet (opcode, 21);
   3660 
   3661                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   3662                 if ((n == 15) || (BitCount (registers) < 1))
   3663                     return false;
   3664 
   3665                 break;
   3666 
   3667             default:
   3668                 return false;
   3669         }
   3670 
   3671         // address = R[n] - 4*BitCount(registers);
   3672 
   3673         int32_t offset = 0;
   3674         addr_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   3675 
   3676         if (!success)
   3677             return false;
   3678 
   3679         addr_t address = Rn - (addr_byte_size * BitCount (registers));
   3680         EmulateInstruction::Context context;
   3681         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3682         RegisterInfo dwarf_reg;
   3683         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, dwarf_reg);
   3684         context.SetRegisterPlusOffset (dwarf_reg, Rn - address);
   3685 
   3686         for (int i = 0; i < 14; ++i)
   3687         {
   3688             if (BitIsSet (registers, i))
   3689             {
   3690                 // R[i] = MemA[address,4]; address = address + 4;
   3691                 context.SetRegisterPlusOffset (dwarf_reg, Rn - (address + offset));
   3692                 uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3693                 if (!success)
   3694                     return false;
   3695 
   3696                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + i, data))
   3697                     return false;
   3698 
   3699                 offset += addr_byte_size;
   3700             }
   3701         }
   3702 
   3703         // if registers<15> == '1' then
   3704         //     LoadWritePC(MemA[address,4]);
   3705         if (BitIsSet (registers, 15))
   3706         {
   3707             context.SetRegisterPlusOffset (dwarf_reg, offset);
   3708             uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3709             if (!success)
   3710                 return false;
   3711             // In ARMv5T and above, this is an interworking branch.
   3712             if (!LoadWritePC(context, data))
   3713                 return false;
   3714         }
   3715 
   3716         // if wback && registers<n> == '0' then R[n] = R[n] - 4*BitCount(registers);
   3717         if (wback && BitIsClear (registers, n))
   3718         {
   3719             if (!success)
   3720                 return false;
   3721 
   3722             offset = (addr_byte_size * BitCount (registers)) * -1;
   3723             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   3724             context.SetImmediateSigned (offset);
   3725             addr_t addr = Rn + offset;
   3726             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, addr))
   3727                 return false;
   3728         }
   3729 
   3730         // if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN; // Only possible for encoding A1
   3731         if (wback && BitIsSet (registers, n))
   3732             return WriteBits32Unknown (n);
   3733     }
   3734     return true;
   3735 }
   3736 
   3737 // LDMIB loads multiple registers from consecutive memory locations using an address from a base register.  The
   3738 // consecutive memory locations start just above this address, and thea ddress of the last of those locations can
   3739 // optinoally be written back to the base register.
   3740 bool
   3741 EmulateInstructionARM::EmulateLDMIB (const uint32_t opcode, const ARMEncoding encoding)
   3742 {
   3743 #if 0
   3744     if ConditionPassed() then
   3745         EncodingSpecificOperations();
   3746         address = R[n] + 4;
   3747 
   3748         for i = 0 to 14
   3749             if registers<i> == '1' then
   3750                   R[i] = MemA[address,4]; address = address + 4;
   3751         if registers<15> == '1' then
   3752             LoadWritePC(MemA[address,4]);
   3753 
   3754         if wback && registers<n> == '0' then R[n] = R[n] + 4*BitCount(registers);
   3755         if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN;
   3756 #endif
   3757 
   3758     bool success = false;
   3759 
   3760     if (ConditionPassed(opcode))
   3761     {
   3762         uint32_t n;
   3763         uint32_t registers = 0;
   3764         bool wback;
   3765         const uint32_t addr_byte_size = GetAddressByteSize();
   3766         switch (encoding)
   3767         {
   3768             case eEncodingA1:
   3769                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   3770                 n = Bits32 (opcode, 19, 16);
   3771                 registers = Bits32 (opcode, 15, 0);
   3772                 wback = BitIsSet (opcode, 21);
   3773 
   3774                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   3775                 if ((n == 15) || (BitCount (registers) < 1))
   3776                     return false;
   3777 
   3778                 break;
   3779             default:
   3780                 return false;
   3781         }
   3782         // address = R[n] + 4;
   3783 
   3784         int32_t offset = 0;
   3785         addr_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   3786 
   3787         if (!success)
   3788             return false;
   3789 
   3790         addr_t address = Rn + addr_byte_size;
   3791 
   3792         EmulateInstruction::Context context;
   3793         context.type = EmulateInstruction::eContextRegisterPlusOffset;
   3794         RegisterInfo dwarf_reg;
   3795         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, dwarf_reg);
   3796         context.SetRegisterPlusOffset (dwarf_reg, offset);
   3797 
   3798         for (int i = 0; i < 14; ++i)
   3799         {
   3800             if (BitIsSet (registers, i))
   3801             {
   3802                 // R[i] = MemA[address,4]; address = address + 4;
   3803 
   3804                 context.SetRegisterPlusOffset (dwarf_reg, offset + addr_byte_size);
   3805                 uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3806                 if (!success)
   3807                     return false;
   3808 
   3809                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + i, data))
   3810                     return false;
   3811 
   3812                 offset += addr_byte_size;
   3813             }
   3814         }
   3815 
   3816         // if registers<15> == '1' then
   3817         //     LoadWritePC(MemA[address,4]);
   3818         if (BitIsSet (registers, 15))
   3819         {
   3820             context.SetRegisterPlusOffset (dwarf_reg, offset);
   3821             uint32_t data = MemARead (context, address + offset, addr_byte_size, 0, &success);
   3822             if (!success)
   3823                 return false;
   3824             // In ARMv5T and above, this is an interworking branch.
   3825             if (!LoadWritePC(context, data))
   3826                 return false;
   3827         }
   3828 
   3829         // if wback && registers<n> == '0' then R[n] = R[n] + 4*BitCount(registers);
   3830         if (wback && BitIsClear (registers, n))
   3831         {
   3832             if (!success)
   3833                 return false;
   3834 
   3835             offset = addr_byte_size * BitCount (registers);
   3836             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   3837             context.SetImmediateSigned (offset);
   3838             addr_t addr = Rn + offset;
   3839             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, addr))
   3840                 return false;
   3841         }
   3842 
   3843         // if wback && registers<n> == '1' then R[n] = bits(32) UNKNOWN; // Only possible for encoding A1
   3844         if (wback && BitIsSet (registers, n))
   3845             return WriteBits32Unknown (n);
   3846     }
   3847     return true;
   3848 }
   3849 
   3850 // Load Register (immediate) calculates an address from a base register value and
   3851 // an immediate offset, loads a word from memory, and writes to a register.
   3852 // LDR (immediate, Thumb)
   3853 bool
   3854 EmulateInstructionARM::EmulateLDRRtRnImm (const uint32_t opcode, const ARMEncoding encoding)
   3855 {
   3856 #if 0
   3857     // ARM pseudo code...
   3858     if (ConditionPassed())
   3859     {
   3860         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   3861         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   3862         address = if index then offset_addr else R[n];
   3863         data = MemU[address,4];
   3864         if wback then R[n] = offset_addr;
   3865         if t == 15 then
   3866             if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   3867         elsif UnalignedSupport() || address<1:0> = '00' then
   3868             R[t] = data;
   3869         else R[t] = bits(32) UNKNOWN; // Can only apply before ARMv7
   3870     }
   3871 #endif
   3872 
   3873     bool success = false;
   3874 
   3875     if (ConditionPassed(opcode))
   3876     {
   3877         uint32_t Rt; // the destination register
   3878         uint32_t Rn; // the base register
   3879         uint32_t imm32; // the immediate offset used to form the address
   3880         addr_t offset_addr; // the offset address
   3881         addr_t address; // the calculated address
   3882         uint32_t data; // the literal data value from memory load
   3883         bool add, index, wback;
   3884         switch (encoding) {
   3885             case eEncodingT1:
   3886                 Rt = Bits32(opcode, 2, 0);
   3887                 Rn = Bits32(opcode, 5, 3);
   3888                 imm32 = Bits32(opcode, 10, 6) << 2; // imm32 = ZeroExtend(imm5:'00', 32);
   3889                 // index = TRUE; add = TRUE; wback = FALSE
   3890                 add = true;
   3891                 index = true;
   3892                 wback = false;
   3893 
   3894                 break;
   3895 
   3896             case eEncodingT2:
   3897                 // t = UInt(Rt); n = 13; imm32 = ZeroExtend(imm8:'00', 32);
   3898                 Rt = Bits32 (opcode, 10, 8);
   3899                 Rn = 13;
   3900                 imm32 = Bits32 (opcode, 7, 0) << 2;
   3901 
   3902                 // index = TRUE; add = TRUE; wback = FALSE;
   3903                 index = true;
   3904                 add = true;
   3905                 wback = false;
   3906 
   3907                 break;
   3908 
   3909             case eEncodingT3:
   3910                 // if Rn == '1111' then SEE LDR (literal);
   3911                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   3912                 Rt = Bits32 (opcode, 15, 12);
   3913                 Rn = Bits32 (opcode, 19, 16);
   3914                 imm32 = Bits32 (opcode, 11, 0);
   3915 
   3916                 // index = TRUE; add = TRUE; wback = FALSE;
   3917                 index = true;
   3918                 add = true;
   3919                 wback = false;
   3920 
   3921                 // if t == 15 && InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   3922                 if ((Rt == 15) && InITBlock() && !LastInITBlock())
   3923                     return false;
   3924 
   3925                 break;
   3926 
   3927             case eEncodingT4:
   3928                 // if Rn == '1111' then SEE LDR (literal);
   3929                 // if P == '1' && U == '1' && W == '0' then SEE LDRT;
   3930                 // if Rn == '1101' && P == '0' && U == '1' && W == '1' && imm8 == '00000100' then SEE POP;
   3931                 // if P == '0' && W == '0' then UNDEFINED;
   3932                 if (BitIsClear (opcode, 10) && BitIsClear (opcode, 8))
   3933                     return false;
   3934 
   3935                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   3936                 Rt = Bits32 (opcode, 15, 12);
   3937                 Rn = Bits32 (opcode, 19, 16);
   3938                 imm32 = Bits32 (opcode, 7, 0);
   3939 
   3940                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   3941                 index = BitIsSet (opcode, 10);
   3942                 add = BitIsSet (opcode, 9);
   3943                 wback = BitIsSet (opcode, 8);
   3944 
   3945                 // if (wback && n == t) || (t == 15 && InITBlock() && !LastInITBlock()) then UNPREDICTABLE;
   3946                 if ((wback && (Rn == Rt)) || ((Rt == 15) && InITBlock() && !LastInITBlock()))
   3947                     return false;
   3948 
   3949                 break;
   3950 
   3951             default:
   3952                 return false;
   3953         }
   3954         uint32_t base = ReadCoreReg (Rn, &success);
   3955         if (!success)
   3956             return false;
   3957         if (add)
   3958             offset_addr = base + imm32;
   3959         else
   3960             offset_addr = base - imm32;
   3961 
   3962         address = (index ? offset_addr : base);
   3963 
   3964         RegisterInfo base_reg;
   3965         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + Rn, base_reg);
   3966         if (wback)
   3967         {
   3968             EmulateInstruction::Context ctx;
   3969             ctx.type = EmulateInstruction::eContextAdjustBaseRegister;
   3970             ctx.SetRegisterPlusOffset (base_reg, (int32_t) (offset_addr - base));
   3971 
   3972             if (!WriteRegisterUnsigned (ctx, eRegisterKindDWARF, dwarf_r0 + Rn, offset_addr))
   3973                 return false;
   3974         }
   3975 
   3976         // Prepare to write to the Rt register.
   3977         EmulateInstruction::Context context;
   3978         context.type = EmulateInstruction::eContextRegisterLoad;
   3979         context.SetRegisterPlusOffset (base_reg, (int32_t) (offset_addr - base));
   3980 
   3981         // Read memory from the address.
   3982         data = MemURead(context, address, 4, 0, &success);
   3983         if (!success)
   3984             return false;
   3985 
   3986         if (Rt == 15)
   3987         {
   3988             if (Bits32(address, 1, 0) == 0)
   3989             {
   3990                 if (!LoadWritePC(context, data))
   3991                     return false;
   3992             }
   3993             else
   3994                 return false;
   3995         }
   3996         else if (UnalignedSupport() || Bits32(address, 1, 0) == 0)
   3997         {
   3998             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + Rt, data))
   3999                 return false;
   4000         }
   4001         else
   4002             WriteBits32Unknown (Rt);
   4003     }
   4004     return true;
   4005 }
   4006 
   4007 // STM (Store Multiple Increment After) stores multiple registers to consecutive memory locations using an address
   4008 // from a base register.  The consecutive memory locations start at this address, and teh address just above the last
   4009 // of those locations can optionally be written back to the base register.
   4010 bool
   4011 EmulateInstructionARM::EmulateSTM (const uint32_t opcode, const ARMEncoding encoding)
   4012 {
   4013 #if 0
   4014     if ConditionPassed() then
   4015         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4016         address = R[n];
   4017 
   4018         for i = 0 to 14
   4019             if registers<i> == '1' then
   4020                 if i == n && wback && i != LowestSetBit(registers) then
   4021                     MemA[address,4] = bits(32) UNKNOWN; // Only possible for encodings T1 and A1
   4022                 else
   4023                     MemA[address,4] = R[i];
   4024                 address = address + 4;
   4025 
   4026         if registers<15> == '1' then // Only possible for encoding A1
   4027             MemA[address,4] = PCStoreValue();
   4028         if wback then R[n] = R[n] + 4*BitCount(registers);
   4029 #endif
   4030 
   4031     bool success = false;
   4032 
   4033     if (ConditionPassed(opcode))
   4034     {
   4035         uint32_t n;
   4036         uint32_t registers = 0;
   4037         bool wback;
   4038         const uint32_t addr_byte_size = GetAddressByteSize();
   4039 
   4040         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4041         switch (encoding)
   4042         {
   4043             case eEncodingT1:
   4044                 // n = UInt(Rn); registers = '00000000':register_list; wback = TRUE;
   4045                 n = Bits32 (opcode, 10, 8);
   4046                 registers = Bits32 (opcode, 7, 0);
   4047                 registers = registers & 0x00ff;  // Make sure the top 8 bits are zeros.
   4048                 wback = true;
   4049 
   4050                 // if BitCount(registers) < 1 then UNPREDICTABLE;
   4051                 if (BitCount (registers) < 1)
   4052                     return false;
   4053 
   4054                 break;
   4055 
   4056             case eEncodingT2:
   4057                 // n = UInt(Rn); registers = '0':M:'0':register_list; wback = (W == '1');
   4058                 n = Bits32 (opcode, 19, 16);
   4059                 registers = Bits32 (opcode, 15, 0);
   4060                 registers = registers & 0x5fff; // Make sure bits 15 & 13 are zeros.
   4061                 wback = BitIsSet (opcode, 21);
   4062 
   4063                 // if n == 15 || BitCount(registers) < 2 then UNPREDICTABLE;
   4064                 if ((n == 15) || (BitCount (registers) < 2))
   4065                     return false;
   4066 
   4067                 // if wback && registers<n> == '1' then UNPREDICTABLE;
   4068                 if (wback && BitIsSet (registers, n))
   4069                     return false;
   4070 
   4071                 break;
   4072 
   4073             case eEncodingA1:
   4074                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   4075                 n = Bits32 (opcode, 19, 16);
   4076                 registers = Bits32 (opcode, 15, 0);
   4077                 wback = BitIsSet (opcode, 21);
   4078 
   4079                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   4080                 if ((n == 15) || (BitCount (registers) < 1))
   4081                     return false;
   4082 
   4083                 break;
   4084 
   4085             default:
   4086                 return false;
   4087         }
   4088 
   4089         // address = R[n];
   4090         int32_t offset = 0;
   4091         const addr_t address = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   4092         if (!success)
   4093             return false;
   4094 
   4095         EmulateInstruction::Context context;
   4096         context.type = EmulateInstruction::eContextRegisterStore;
   4097         RegisterInfo base_reg;
   4098         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   4099 
   4100         // for i = 0 to 14
   4101         uint32_t lowest_set_bit = 14;
   4102         for (uint32_t i = 0; i < 14; ++i)
   4103         {
   4104             // if registers<i> == '1' then
   4105             if (BitIsSet (registers, i))
   4106             {
   4107                   if (i < lowest_set_bit)
   4108                       lowest_set_bit = i;
   4109                   // if i == n && wback && i != LowestSetBit(registers) then
   4110                   if ((i == n) && wback && (i != lowest_set_bit))
   4111                       // MemA[address,4] = bits(32) UNKNOWN; // Only possible for encodings T1 and A1
   4112                       WriteBits32UnknownToMemory (address + offset);
   4113                   else
   4114                   {
   4115                      // MemA[address,4] = R[i];
   4116                       uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + i, 0, &success);
   4117                       if (!success)
   4118                           return false;
   4119 
   4120                       RegisterInfo data_reg;
   4121                       GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + i, data_reg);
   4122                       context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, offset);
   4123                       if (!MemAWrite (context, address + offset, data, addr_byte_size))
   4124                           return false;
   4125                   }
   4126 
   4127                   // address = address + 4;
   4128                   offset += addr_byte_size;
   4129             }
   4130         }
   4131 
   4132         // if registers<15> == '1' then // Only possible for encoding A1
   4133         //     MemA[address,4] = PCStoreValue();
   4134         if (BitIsSet (registers, 15))
   4135         {
   4136             RegisterInfo pc_reg;
   4137             GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, pc_reg);
   4138             context.SetRegisterPlusOffset (pc_reg, 8);
   4139             const uint32_t pc = ReadCoreReg (PC_REG, &success);
   4140             if (!success)
   4141                 return false;
   4142 
   4143             if (!MemAWrite (context, address + offset, pc, addr_byte_size))
   4144                 return false;
   4145         }
   4146 
   4147         // if wback then R[n] = R[n] + 4*BitCount(registers);
   4148         if (wback)
   4149         {
   4150             offset = addr_byte_size * BitCount (registers);
   4151             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   4152             context.SetImmediateSigned (offset);
   4153             addr_t data = address + offset;
   4154             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, data))
   4155                 return false;
   4156         }
   4157     }
   4158     return true;
   4159 }
   4160 
   4161 // STMDA (Store Multiple Decrement After) stores multiple registers to consecutive memory locations using an address
   4162 // from a base register.  The consecutive memory locations end at this address, and the address just below the lowest
   4163 // of those locations can optionally be written back to the base register.
   4164 bool
   4165 EmulateInstructionARM::EmulateSTMDA (const uint32_t opcode, const ARMEncoding encoding)
   4166 {
   4167 #if 0
   4168     if ConditionPassed() then
   4169         EncodingSpecificOperations();
   4170         address = R[n] - 4*BitCount(registers) + 4;
   4171 
   4172         for i = 0 to 14
   4173             if registers<i> == '1' then
   4174                 if i == n && wback && i != LowestSetBit(registers) then
   4175                     MemA[address,4] = bits(32) UNKNOWN;
   4176                 else
   4177                     MemA[address,4] = R[i];
   4178                 address = address + 4;
   4179 
   4180         if registers<15> == '1' then
   4181             MemA[address,4] = PCStoreValue();
   4182 
   4183         if wback then R[n] = R[n] - 4*BitCount(registers);
   4184 #endif
   4185 
   4186     bool success = false;
   4187 
   4188     if (ConditionPassed(opcode))
   4189     {
   4190         uint32_t n;
   4191         uint32_t registers = 0;
   4192         bool wback;
   4193         const uint32_t addr_byte_size = GetAddressByteSize();
   4194 
   4195         // EncodingSpecificOperations();
   4196         switch (encoding)
   4197         {
   4198             case eEncodingA1:
   4199                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   4200                 n = Bits32 (opcode, 19, 16);
   4201                 registers = Bits32 (opcode, 15, 0);
   4202                 wback = BitIsSet (opcode, 21);
   4203 
   4204                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   4205                 if ((n == 15) || (BitCount (registers) < 1))
   4206                     return false;
   4207                 break;
   4208             default:
   4209                 return false;
   4210         }
   4211 
   4212         // address = R[n] - 4*BitCount(registers) + 4;
   4213         int32_t offset = 0;
   4214         addr_t Rn = ReadCoreReg (n, &success);
   4215         if (!success)
   4216             return false;
   4217 
   4218         addr_t address = Rn - (addr_byte_size * BitCount (registers)) + 4;
   4219 
   4220         EmulateInstruction::Context context;
   4221         context.type = EmulateInstruction::eContextRegisterStore;
   4222         RegisterInfo base_reg;
   4223         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   4224 
   4225         // for i = 0 to 14
   4226         uint32_t lowest_bit_set = 14;
   4227         for (uint32_t i = 0; i < 14; ++i)
   4228         {
   4229             // if registers<i> == '1' then
   4230             if (BitIsSet (registers, i))
   4231             {
   4232                 if (i < lowest_bit_set)
   4233                     lowest_bit_set = i;
   4234                 //if i == n && wback && i != LowestSetBit(registers) then
   4235                 if ((i == n) && wback && (i != lowest_bit_set))
   4236                     // MemA[address,4] = bits(32) UNKNOWN;
   4237                     WriteBits32UnknownToMemory (address + offset);
   4238                 else
   4239                 {
   4240                     // MemA[address,4] = R[i];
   4241                     uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + i, 0, &success);
   4242                     if (!success)
   4243                         return false;
   4244 
   4245                     RegisterInfo data_reg;
   4246                     GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + i, data_reg);
   4247                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, Rn - (address + offset));
   4248                     if (!MemAWrite (context, address + offset, data, addr_byte_size))
   4249                         return false;
   4250                 }
   4251 
   4252                 // address = address + 4;
   4253                 offset += addr_byte_size;
   4254             }
   4255         }
   4256 
   4257         // if registers<15> == '1' then
   4258         //    MemA[address,4] = PCStoreValue();
   4259         if (BitIsSet (registers, 15))
   4260         {
   4261             RegisterInfo pc_reg;
   4262             GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, pc_reg);
   4263             context.SetRegisterPlusOffset (pc_reg, 8);
   4264             const uint32_t pc = ReadCoreReg (PC_REG, &success);
   4265             if (!success)
   4266                 return false;
   4267 
   4268             if (!MemAWrite (context, address + offset, pc, addr_byte_size))
   4269                 return false;
   4270         }
   4271 
   4272         // if wback then R[n] = R[n] - 4*BitCount(registers);
   4273         if (wback)
   4274         {
   4275             offset = (addr_byte_size * BitCount (registers)) * -1;
   4276             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   4277             context.SetImmediateSigned (offset);
   4278             addr_t data = Rn + offset;
   4279             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, data))
   4280                 return false;
   4281         }
   4282     }
   4283     return true;
   4284 }
   4285 
   4286 // STMDB (Store Multiple Decrement Before) stores multiple registers to consecutive memory locations using an address
   4287 // from a base register.  The consecutive memory locations end just below this address, and the address of the first of
   4288 // those locations can optionally be written back to the base register.
   4289 bool
   4290 EmulateInstructionARM::EmulateSTMDB (const uint32_t opcode, const ARMEncoding encoding)
   4291 {
   4292 #if 0
   4293     if ConditionPassed() then
   4294         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4295         address = R[n] - 4*BitCount(registers);
   4296 
   4297         for i = 0 to 14
   4298             if registers<i> == '1' then
   4299                 if i == n && wback && i != LowestSetBit(registers) then
   4300                     MemA[address,4] = bits(32) UNKNOWN; // Only possible for encoding A1
   4301                 else
   4302                     MemA[address,4] = R[i];
   4303                 address = address + 4;
   4304 
   4305         if registers<15> == '1' then // Only possible for encoding A1
   4306             MemA[address,4] = PCStoreValue();
   4307 
   4308         if wback then R[n] = R[n] - 4*BitCount(registers);
   4309 #endif
   4310 
   4311 
   4312     bool success = false;
   4313 
   4314     if (ConditionPassed(opcode))
   4315     {
   4316         uint32_t n;
   4317         uint32_t registers = 0;
   4318         bool wback;
   4319         const uint32_t addr_byte_size = GetAddressByteSize();
   4320 
   4321         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4322         switch (encoding)
   4323         {
   4324             case eEncodingT1:
   4325                 // if W == '1' && Rn == '1101' then SEE PUSH;
   4326                 if ((BitIsSet (opcode, 21)) && (Bits32 (opcode, 19, 16) == 13))
   4327                 {
   4328                     // See PUSH
   4329                 }
   4330                 // n = UInt(Rn); registers = '0':M:'0':register_list; wback = (W == '1');
   4331                 n = Bits32 (opcode, 19, 16);
   4332                 registers = Bits32 (opcode, 15, 0);
   4333                 registers = registers & 0x5fff;  // Make sure bits 15 & 13 are zeros.
   4334                 wback = BitIsSet (opcode, 21);
   4335                 // if n == 15 || BitCount(registers) < 2 then UNPREDICTABLE;
   4336                 if ((n == 15) || BitCount (registers) < 2)
   4337                     return false;
   4338                 // if wback && registers<n> == '1' then UNPREDICTABLE;
   4339                 if (wback && BitIsSet (registers, n))
   4340                     return false;
   4341                 break;
   4342 
   4343             case eEncodingA1:
   4344                 // if W == '1' && Rn == '1101 && BitCount(register_list) >= 2 then SEE PUSH;
   4345                 if (BitIsSet (opcode, 21) && (Bits32 (opcode, 19, 16) == 13) && BitCount (Bits32 (opcode, 15, 0)) >= 2)
   4346                 {
   4347                     // See Push
   4348                 }
   4349                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   4350                 n = Bits32 (opcode, 19, 16);
   4351                 registers = Bits32 (opcode, 15, 0);
   4352                 wback = BitIsSet (opcode, 21);
   4353                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   4354                 if ((n == 15) || BitCount (registers) < 1)
   4355                     return false;
   4356                 break;
   4357 
   4358             default:
   4359                 return false;
   4360         }
   4361 
   4362         // address = R[n] - 4*BitCount(registers);
   4363 
   4364         int32_t offset = 0;
   4365         addr_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   4366         if (!success)
   4367         return false;
   4368 
   4369         addr_t address = Rn - (addr_byte_size * BitCount (registers));
   4370 
   4371         EmulateInstruction::Context context;
   4372         context.type = EmulateInstruction::eContextRegisterStore;
   4373         RegisterInfo base_reg;
   4374         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   4375 
   4376         // for i = 0 to 14
   4377         uint32_t lowest_set_bit = 14;
   4378         for (uint32_t i = 0; i < 14; ++i)
   4379         {
   4380             // if registers<i> == '1' then
   4381             if (BitIsSet (registers, i))
   4382             {
   4383                 if (i < lowest_set_bit)
   4384                     lowest_set_bit = i;
   4385                 // if i == n && wback && i != LowestSetBit(registers) then
   4386                 if ((i == n) && wback && (i != lowest_set_bit))
   4387                     // MemA[address,4] = bits(32) UNKNOWN; // Only possible for encoding A1
   4388                     WriteBits32UnknownToMemory (address + offset);
   4389                 else
   4390                 {
   4391                     // MemA[address,4] = R[i];
   4392                     uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + i, 0, &success);
   4393                     if (!success)
   4394                         return false;
   4395 
   4396                     RegisterInfo data_reg;
   4397                     GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + i, data_reg);
   4398                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, Rn - (address + offset));
   4399                     if (!MemAWrite (context, address + offset, data, addr_byte_size))
   4400                         return false;
   4401                 }
   4402 
   4403                 // address = address + 4;
   4404                 offset += addr_byte_size;
   4405             }
   4406         }
   4407 
   4408         // if registers<15> == '1' then // Only possible for encoding A1
   4409         //     MemA[address,4] = PCStoreValue();
   4410         if (BitIsSet (registers, 15))
   4411         {
   4412             RegisterInfo pc_reg;
   4413             GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, pc_reg);
   4414             context.SetRegisterPlusOffset (pc_reg, 8);
   4415             const uint32_t pc = ReadCoreReg (PC_REG, &success);
   4416             if (!success)
   4417                 return false;
   4418 
   4419             if (!MemAWrite (context, address + offset, pc, addr_byte_size))
   4420                 return false;
   4421         }
   4422 
   4423         // if wback then R[n] = R[n] - 4*BitCount(registers);
   4424         if (wback)
   4425         {
   4426             offset = (addr_byte_size * BitCount (registers)) * -1;
   4427             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   4428             context.SetImmediateSigned (offset);
   4429             addr_t data = Rn + offset;
   4430             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, data))
   4431                 return false;
   4432         }
   4433     }
   4434     return true;
   4435 }
   4436 
   4437 // STMIB (Store Multiple Increment Before) stores multiple registers to consecutive memory locations using an address
   4438 // from a base register.  The consecutive memory locations start just above this address, and the address of the last
   4439 // of those locations can optionally be written back to the base register.
   4440 bool
   4441 EmulateInstructionARM::EmulateSTMIB (const uint32_t opcode, const ARMEncoding encoding)
   4442 {
   4443 #if 0
   4444     if ConditionPassed() then
   4445         EncodingSpecificOperations();
   4446         address = R[n] + 4;
   4447 
   4448         for i = 0 to 14
   4449             if registers<i> == '1' then
   4450                 if i == n && wback && i != LowestSetBit(registers) then
   4451                     MemA[address,4] = bits(32) UNKNOWN;
   4452                 else
   4453                     MemA[address,4] = R[i];
   4454                 address = address + 4;
   4455 
   4456         if registers<15> == '1' then
   4457             MemA[address,4] = PCStoreValue();
   4458 
   4459         if wback then R[n] = R[n] + 4*BitCount(registers);
   4460 #endif
   4461 
   4462     bool success = false;
   4463 
   4464     if (ConditionPassed(opcode))
   4465     {
   4466         uint32_t n;
   4467         uint32_t registers = 0;
   4468         bool wback;
   4469         const uint32_t addr_byte_size = GetAddressByteSize();
   4470 
   4471         // EncodingSpecificOperations();
   4472         switch (encoding)
   4473         {
   4474             case eEncodingA1:
   4475                 // n = UInt(Rn); registers = register_list; wback = (W == '1');
   4476                 n = Bits32 (opcode, 19, 16);
   4477                 registers = Bits32 (opcode, 15, 0);
   4478                 wback = BitIsSet (opcode, 21);
   4479 
   4480                 // if n == 15 || BitCount(registers) < 1 then UNPREDICTABLE;
   4481                 if ((n == 15) && (BitCount (registers) < 1))
   4482                     return false;
   4483                 break;
   4484             default:
   4485                 return false;
   4486         }
   4487         // address = R[n] + 4;
   4488 
   4489         int32_t offset = 0;
   4490         addr_t Rn = ReadCoreReg (n, &success);
   4491         if (!success)
   4492             return false;
   4493 
   4494         addr_t address = Rn + addr_byte_size;
   4495 
   4496         EmulateInstruction::Context context;
   4497         context.type = EmulateInstruction::eContextRegisterStore;
   4498         RegisterInfo base_reg;
   4499         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   4500 
   4501         uint32_t lowest_set_bit = 14;
   4502         // for i = 0 to 14
   4503         for (uint32_t i = 0; i < 14; ++i)
   4504         {
   4505             // if registers<i> == '1' then
   4506             if (BitIsSet (registers, i))
   4507             {
   4508                 if (i < lowest_set_bit)
   4509                     lowest_set_bit = i;
   4510                 // if i == n && wback && i != LowestSetBit(registers) then
   4511                 if ((i == n) && wback && (i != lowest_set_bit))
   4512                     // MemA[address,4] = bits(32) UNKNOWN;
   4513                     WriteBits32UnknownToMemory (address + offset);
   4514                 // else
   4515                 else
   4516                 {
   4517                     // MemA[address,4] = R[i];
   4518                     uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + i, 0, &success);
   4519                     if (!success)
   4520                         return false;
   4521 
   4522                     RegisterInfo data_reg;
   4523                     GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + i, data_reg);
   4524                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, offset + addr_byte_size);
   4525                     if (!MemAWrite (context, address + offset, data, addr_byte_size))
   4526                         return false;
   4527                 }
   4528 
   4529                 // address = address + 4;
   4530                 offset += addr_byte_size;
   4531             }
   4532         }
   4533 
   4534         // if registers<15> == '1' then
   4535             // MemA[address,4] = PCStoreValue();
   4536         if (BitIsSet (registers, 15))
   4537         {
   4538             RegisterInfo pc_reg;
   4539             GetRegisterInfo (eRegisterKindDWARF, dwarf_pc, pc_reg);
   4540             context.SetRegisterPlusOffset (pc_reg, 8);
   4541             const uint32_t pc = ReadCoreReg (PC_REG, &success);
   4542             if (!success)
   4543             return false;
   4544 
   4545             if (!MemAWrite (context, address + offset, pc, addr_byte_size))
   4546                 return false;
   4547         }
   4548 
   4549         // if wback then R[n] = R[n] + 4*BitCount(registers);
   4550         if (wback)
   4551         {
   4552             offset = addr_byte_size * BitCount (registers);
   4553             context.type = EmulateInstruction::eContextAdjustBaseRegister;
   4554             context.SetImmediateSigned (offset);
   4555             addr_t data = Rn + offset;
   4556             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, data))
   4557                 return false;
   4558         }
   4559     }
   4560     return true;
   4561 }
   4562 
   4563 // STR (store immediate) calcualtes an address from a base register value and an immediate offset, and stores a word
   4564 // from a register to memory.  It can use offset, post-indexed, or pre-indexed addressing.
   4565 bool
   4566 EmulateInstructionARM::EmulateSTRThumb (const uint32_t opcode, const ARMEncoding encoding)
   4567 {
   4568 #if 0
   4569     if ConditionPassed() then
   4570         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4571         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   4572         address = if index then offset_addr else R[n];
   4573         if UnalignedSupport() || address<1:0> == '00' then
   4574             MemU[address,4] = R[t];
   4575         else // Can only occur before ARMv7
   4576             MemU[address,4] = bits(32) UNKNOWN;
   4577         if wback then R[n] = offset_addr;
   4578 #endif
   4579 
   4580     bool success = false;
   4581 
   4582     if (ConditionPassed(opcode))
   4583     {
   4584         const uint32_t addr_byte_size = GetAddressByteSize();
   4585 
   4586         uint32_t t;
   4587         uint32_t n;
   4588         uint32_t imm32;
   4589         bool index;
   4590         bool add;
   4591         bool wback;
   4592         // EncodingSpecificOperations (); NullCheckIfThumbEE(n);
   4593         switch (encoding)
   4594         {
   4595             case eEncodingT1:
   4596                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm5:'00', 32);
   4597                 t = Bits32 (opcode, 2, 0);
   4598                 n = Bits32 (opcode, 5, 3);
   4599                 imm32 = Bits32 (opcode, 10, 6) << 2;
   4600 
   4601                 // index = TRUE; add = TRUE; wback = FALSE;
   4602                 index = true;
   4603                 add = false;
   4604                 wback = false;
   4605                 break;
   4606 
   4607             case eEncodingT2:
   4608                 // t = UInt(Rt); n = 13; imm32 = ZeroExtend(imm8:'00', 32);
   4609                 t = Bits32 (opcode, 10, 8);
   4610                 n = 13;
   4611                 imm32 = Bits32 (opcode, 7, 0) << 2;
   4612 
   4613                 // index = TRUE; add = TRUE; wback = FALSE;
   4614                 index = true;
   4615                 add = true;
   4616                 wback = false;
   4617                 break;
   4618 
   4619             case eEncodingT3:
   4620                 // if Rn == '1111' then UNDEFINED;
   4621                 if (Bits32 (opcode, 19, 16) == 15)
   4622                     return false;
   4623 
   4624                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   4625                 t = Bits32 (opcode, 15, 12);
   4626                 n = Bits32 (opcode, 19, 16);
   4627                 imm32 = Bits32 (opcode, 11, 0);
   4628 
   4629                 // index = TRUE; add = TRUE; wback = FALSE;
   4630                 index = true;
   4631                 add = true;
   4632                 wback = false;
   4633 
   4634                 // if t == 15 then UNPREDICTABLE;
   4635                 if (t == 15)
   4636                     return false;
   4637                 break;
   4638 
   4639             case eEncodingT4:
   4640                 // if P == '1' && U == '1' && W == '0' then SEE STRT;
   4641                 // if Rn == '1101' && P == '1' && U == '0' && W == '1' && imm8 == '00000100' then SEE PUSH;
   4642                 // if Rn == '1111' || (P == '0' && W == '0') then UNDEFINED;
   4643                 if ((Bits32 (opcode, 19, 16) == 15)
   4644                       || (BitIsClear (opcode, 10) && BitIsClear (opcode, 8)))
   4645                     return false;
   4646 
   4647                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   4648                 t = Bits32 (opcode, 15, 12);
   4649                 n = Bits32 (opcode, 19, 16);
   4650                 imm32 = Bits32 (opcode, 7, 0);
   4651 
   4652                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   4653                 index = BitIsSet (opcode, 10);
   4654                 add = BitIsSet (opcode, 9);
   4655                 wback = BitIsSet (opcode, 8);
   4656 
   4657                 // if t == 15 || (wback && n == t) then UNPREDICTABLE;
   4658                 if ((t == 15) || (wback && (n == t)))
   4659                     return false;
   4660                 break;
   4661 
   4662             default:
   4663                 return false;
   4664         }
   4665 
   4666         addr_t offset_addr;
   4667         addr_t address;
   4668 
   4669         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   4670         uint32_t base_address = ReadCoreReg (n, &success);
   4671         if (!success)
   4672             return false;
   4673 
   4674         if (add)
   4675             offset_addr = base_address + imm32;
   4676         else
   4677             offset_addr = base_address - imm32;
   4678 
   4679         // address = if index then offset_addr else R[n];
   4680         if (index)
   4681             address = offset_addr;
   4682         else
   4683             address = base_address;
   4684 
   4685         EmulateInstruction::Context context;
   4686         context.type = eContextRegisterStore;
   4687         RegisterInfo base_reg;
   4688         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   4689 
   4690         // if UnalignedSupport() || address<1:0> == '00' then
   4691         if (UnalignedSupport () || (BitIsClear (address, 1) && BitIsClear (address, 0)))
   4692         {
   4693             // MemU[address,4] = R[t];
   4694             uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + t, 0, &success);
   4695             if (!success)
   4696                 return false;
   4697 
   4698             RegisterInfo data_reg;
   4699             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   4700             int32_t offset = address - base_address;
   4701             context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, offset);
   4702             if (!MemUWrite (context, address, data, addr_byte_size))
   4703                 return false;
   4704         }
   4705         else
   4706         {
   4707             // MemU[address,4] = bits(32) UNKNOWN;
   4708             WriteBits32UnknownToMemory (address);
   4709         }
   4710 
   4711         // if wback then R[n] = offset_addr;
   4712         if (wback)
   4713         {
   4714             context.type = eContextRegisterLoad;
   4715             context.SetAddress (offset_addr);
   4716             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   4717                 return false;
   4718         }
   4719     }
   4720     return true;
   4721 }
   4722 
   4723 // STR (Store Register) calculates an address from a base register value and an offset register value, stores a
   4724 // word from a register to memory.   The offset register value can optionally be shifted.
   4725 bool
   4726 EmulateInstructionARM::EmulateSTRRegister (const uint32_t opcode, const ARMEncoding encoding)
   4727 {
   4728 #if 0
   4729     if ConditionPassed() then
   4730         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4731         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   4732         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   4733         address = if index then offset_addr else R[n];
   4734         if t == 15 then // Only possible for encoding A1
   4735             data = PCStoreValue();
   4736         else
   4737             data = R[t];
   4738         if UnalignedSupport() || address<1:0> == '00' || CurrentInstrSet() == InstrSet_ARM then
   4739             MemU[address,4] = data;
   4740         else // Can only occur before ARMv7
   4741             MemU[address,4] = bits(32) UNKNOWN;
   4742         if wback then R[n] = offset_addr;
   4743 #endif
   4744 
   4745     bool success = false;
   4746 
   4747     if (ConditionPassed(opcode))
   4748     {
   4749         const uint32_t addr_byte_size = GetAddressByteSize();
   4750 
   4751         uint32_t t;
   4752         uint32_t n;
   4753         uint32_t m;
   4754         ARM_ShifterType shift_t;
   4755         uint32_t shift_n;
   4756         bool index;
   4757         bool add;
   4758         bool wback;
   4759 
   4760         // EncodingSpecificOperations (); NullCheckIfThumbEE(n);
   4761         switch (encoding)
   4762         {
   4763             case eEncodingT1:
   4764                 // if CurrentInstrSet() == InstrSet_ThumbEE then SEE "Modified operation in ThumbEE";
   4765                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   4766                 t = Bits32 (opcode, 2, 0);
   4767                 n = Bits32 (opcode, 5, 3);
   4768                 m = Bits32 (opcode, 8, 6);
   4769 
   4770                 // index = TRUE; add = TRUE; wback = FALSE;
   4771                 index = true;
   4772                 add = true;
   4773                 wback = false;
   4774 
   4775                 // (shift_t, shift_n) = (SRType_LSL, 0);
   4776                 shift_t = SRType_LSL;
   4777                 shift_n = 0;
   4778                 break;
   4779 
   4780             case eEncodingT2:
   4781                 // if Rn == '1111' then UNDEFINED;
   4782                 if (Bits32 (opcode, 19, 16) == 15)
   4783                     return false;
   4784 
   4785                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   4786                 t = Bits32 (opcode, 15, 12);
   4787                 n = Bits32 (opcode, 19, 16);
   4788                 m = Bits32 (opcode, 3, 0);
   4789 
   4790                 // index = TRUE; add = TRUE; wback = FALSE;
   4791                 index = true;
   4792                 add = true;
   4793                 wback = false;
   4794 
   4795                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   4796                 shift_t = SRType_LSL;
   4797                 shift_n = Bits32 (opcode, 5, 4);
   4798 
   4799                 // if t == 15 || BadReg(m) then UNPREDICTABLE;
   4800                 if ((t == 15) || (BadReg (m)))
   4801                     return false;
   4802                 break;
   4803 
   4804             case eEncodingA1:
   4805             {
   4806                 // if P == '0' && W == '1' then SEE STRT;
   4807                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   4808                 t = Bits32 (opcode, 15, 12);
   4809                 n = Bits32 (opcode, 19, 16);
   4810                 m = Bits32 (opcode, 3, 0);
   4811 
   4812                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   4813                 index = BitIsSet (opcode, 24);
   4814                 add = BitIsSet (opcode, 23);
   4815                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   4816 
   4817                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   4818                 uint32_t typ = Bits32 (opcode, 6, 5);
   4819                 uint32_t imm5 = Bits32 (opcode, 11, 7);
   4820                 shift_n = DecodeImmShift(typ, imm5, shift_t);
   4821 
   4822                 // if m == 15 then UNPREDICTABLE;
   4823                 if (m == 15)
   4824                     return false;
   4825 
   4826                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   4827                 if (wback && ((n == 15) || (n == t)))
   4828                     return false;
   4829 
   4830                 break;
   4831             }
   4832             default:
   4833                 return false;
   4834         }
   4835 
   4836         addr_t offset_addr;
   4837         addr_t address;
   4838         int32_t offset = 0;
   4839 
   4840         addr_t base_address = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   4841         if (!success)
   4842             return false;
   4843 
   4844         uint32_t Rm_data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   4845         if (!success)
   4846             return false;
   4847 
   4848         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   4849         offset = Shift (Rm_data, shift_t, shift_n, APSR_C, &success);
   4850         if (!success)
   4851             return false;
   4852 
   4853         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   4854         if (add)
   4855             offset_addr = base_address + offset;
   4856         else
   4857             offset_addr = base_address - offset;
   4858 
   4859         // address = if index then offset_addr else R[n];
   4860         if (index)
   4861             address = offset_addr;
   4862         else
   4863             address = base_address;
   4864 
   4865         uint32_t data;
   4866         // if t == 15 then // Only possible for encoding A1
   4867         if (t == 15)
   4868             // data = PCStoreValue();
   4869             data = ReadCoreReg (PC_REG, &success);
   4870         else
   4871             // data = R[t];
   4872             data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + t, 0, &success);
   4873 
   4874         if (!success)
   4875             return false;
   4876 
   4877         EmulateInstruction::Context context;
   4878         context.type = eContextRegisterStore;
   4879 
   4880         // if UnalignedSupport() || address<1:0> == '00' || CurrentInstrSet() == InstrSet_ARM then
   4881         if (UnalignedSupport ()
   4882             || (BitIsClear (address, 1) && BitIsClear (address, 0))
   4883             || CurrentInstrSet() == eModeARM)
   4884         {
   4885             // MemU[address,4] = data;
   4886 
   4887             RegisterInfo base_reg;
   4888             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 +  n, base_reg);
   4889 
   4890             RegisterInfo data_reg;
   4891             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   4892 
   4893             context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - base_address);
   4894             if (!MemUWrite (context, address, data, addr_byte_size))
   4895                 return false;
   4896 
   4897         }
   4898         else
   4899             // MemU[address,4] = bits(32) UNKNOWN;
   4900             WriteBits32UnknownToMemory (address);
   4901 
   4902         // if wback then R[n] = offset_addr;
   4903         if (wback)
   4904         {
   4905             context.type = eContextRegisterLoad;
   4906             context.SetAddress (offset_addr);
   4907             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   4908                 return false;
   4909         }
   4910 
   4911     }
   4912     return true;
   4913 }
   4914 
   4915 bool
   4916 EmulateInstructionARM::EmulateSTRBThumb (const uint32_t opcode, const ARMEncoding encoding)
   4917 {
   4918 #if 0
   4919     if ConditionPassed() then
   4920         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4921         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   4922         address = if index then offset_addr else R[n];
   4923         MemU[address,1] = R[t]<7:0>;
   4924         if wback then R[n] = offset_addr;
   4925 #endif
   4926 
   4927 
   4928     bool success = false;
   4929 
   4930     if (ConditionPassed(opcode))
   4931     {
   4932         uint32_t t;
   4933         uint32_t n;
   4934         uint32_t imm32;
   4935         bool index;
   4936         bool add;
   4937         bool wback;
   4938         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   4939         switch (encoding)
   4940         {
   4941             case eEncodingT1:
   4942                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm5, 32);
   4943                 t = Bits32 (opcode, 2, 0);
   4944                 n = Bits32 (opcode, 5, 3);
   4945                 imm32 = Bits32 (opcode, 10, 6);
   4946 
   4947                 // index = TRUE; add = TRUE; wback = FALSE;
   4948                 index = true;
   4949                 add = true;
   4950                 wback = false;
   4951                 break;
   4952 
   4953             case eEncodingT2:
   4954                 // if Rn == '1111' then UNDEFINED;
   4955                 if (Bits32 (opcode, 19, 16) == 15)
   4956                     return false;
   4957 
   4958                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   4959                 t = Bits32 (opcode, 15, 12);
   4960                 n = Bits32 (opcode, 19, 16);
   4961                 imm32 = Bits32 (opcode, 11, 0);
   4962 
   4963                 // index = TRUE; add = TRUE; wback = FALSE;
   4964                 index = true;
   4965                 add = true;
   4966                 wback = false;
   4967 
   4968                 // if BadReg(t) then UNPREDICTABLE;
   4969                 if (BadReg (t))
   4970                     return false;
   4971                 break;
   4972 
   4973             case eEncodingT3:
   4974                 // if P == '1' && U == '1' && W == '0' then SEE STRBT;
   4975                 // if Rn == '1111' || (P == '0' && W == '0') then UNDEFINED;
   4976                 if (Bits32 (opcode, 19, 16) == 15)
   4977                     return false;
   4978 
   4979                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   4980                 t = Bits32 (opcode, 15, 12);
   4981                 n = Bits32 (opcode, 19, 16);
   4982                 imm32 = Bits32 (opcode, 7, 0);
   4983 
   4984                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   4985                 index = BitIsSet (opcode, 10);
   4986                 add = BitIsSet (opcode, 9);
   4987                 wback = BitIsSet (opcode, 8);
   4988 
   4989                 // if BadReg(t) || (wback && n == t) then UNPREDICTABLE
   4990                 if ((BadReg (t)) || (wback && (n == t)))
   4991                     return false;
   4992                 break;
   4993 
   4994             default:
   4995                 return false;
   4996         }
   4997 
   4998         addr_t offset_addr;
   4999         addr_t address;
   5000         addr_t base_address = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   5001         if (!success)
   5002             return false;
   5003 
   5004         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   5005         if (add)
   5006             offset_addr = base_address + imm32;
   5007         else
   5008             offset_addr = base_address - imm32;
   5009 
   5010         // address = if index then offset_addr else R[n];
   5011         if (index)
   5012             address = offset_addr;
   5013         else
   5014             address = base_address;
   5015 
   5016         // MemU[address,1] = R[t]<7:0>
   5017         RegisterInfo base_reg;
   5018         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   5019 
   5020         RegisterInfo data_reg;
   5021         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   5022 
   5023         EmulateInstruction::Context context;
   5024         context.type = eContextRegisterStore;
   5025         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - base_address);
   5026 
   5027         uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + t, 0, &success);
   5028         if (!success)
   5029             return false;
   5030 
   5031         data = Bits32 (data, 7, 0);
   5032 
   5033         if (!MemUWrite (context, address, data, 1))
   5034             return false;
   5035 
   5036         // if wback then R[n] = offset_addr;
   5037         if (wback)
   5038         {
   5039             context.type = eContextRegisterLoad;
   5040             context.SetAddress (offset_addr);
   5041             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   5042                 return false;
   5043         }
   5044 
   5045     }
   5046 
   5047     return true;
   5048 }
   5049 
   5050 // STRH (register) calculates an address from a base register value and an offset register value, and stores a
   5051 // halfword from a register to memory.  The offset register alue can be shifted left by 0, 1, 2, or 3 bits.
   5052 bool
   5053 EmulateInstructionARM::EmulateSTRHRegister (const uint32_t opcode, const ARMEncoding encoding)
   5054 {
   5055 #if 0
   5056     if ConditionPassed() then
   5057         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   5058         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   5059         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   5060         address = if index then offset_addr else R[n];
   5061         if UnalignedSupport() || address<0> == '0' then
   5062             MemU[address,2] = R[t]<15:0>;
   5063         else // Can only occur before ARMv7
   5064             MemU[address,2] = bits(16) UNKNOWN;
   5065         if wback then R[n] = offset_addr;
   5066 #endif
   5067 
   5068     bool success = false;
   5069 
   5070     if (ConditionPassed(opcode))
   5071     {
   5072         uint32_t t;
   5073         uint32_t n;
   5074         uint32_t m;
   5075         bool index;
   5076         bool add;
   5077         bool wback;
   5078         ARM_ShifterType shift_t;
   5079         uint32_t shift_n;
   5080 
   5081         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   5082         switch (encoding)
   5083         {
   5084             case eEncodingT1:
   5085                 // if CurrentInstrSet() == InstrSet_ThumbEE then SEE "Modified operation in ThumbEE";
   5086                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   5087                 t = Bits32 (opcode, 2, 0);
   5088                 n = Bits32 (opcode, 5, 3);
   5089                 m = Bits32 (opcode, 8, 6);
   5090 
   5091                 // index = TRUE; add = TRUE; wback = FALSE;
   5092                 index = true;
   5093                 add = true;
   5094                 wback = false;
   5095 
   5096                 // (shift_t, shift_n) = (SRType_LSL, 0);
   5097                 shift_t = SRType_LSL;
   5098                 shift_n = 0;
   5099 
   5100                 break;
   5101 
   5102             case eEncodingT2:
   5103                 // if Rn == '1111' then UNDEFINED;
   5104                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   5105                 t = Bits32 (opcode, 15, 12);
   5106                 n = Bits32 (opcode, 19, 16);
   5107                 m = Bits32 (opcode, 3, 0);
   5108                 if (n == 15)
   5109                     return false;
   5110 
   5111                 // index = TRUE; add = TRUE; wback = FALSE;
   5112                 index = true;
   5113                 add = true;
   5114                 wback = false;
   5115 
   5116                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   5117                 shift_t = SRType_LSL;
   5118                 shift_n = Bits32 (opcode, 5, 4);
   5119 
   5120                 // if BadReg(t) || BadReg(m) then UNPREDICTABLE;
   5121                 if (BadReg (t) || BadReg (m))
   5122                     return false;
   5123 
   5124                 break;
   5125 
   5126             case eEncodingA1:
   5127                 // if P == '0' && W == '1' then SEE STRHT;
   5128                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   5129                 t = Bits32 (opcode, 15, 12);
   5130                 n = Bits32 (opcode, 19, 16);
   5131                 m = Bits32 (opcode, 3, 0);
   5132 
   5133                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   5134                 index = BitIsSet (opcode, 24);
   5135                 add = BitIsSet (opcode, 23);
   5136                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   5137 
   5138                 // (shift_t, shift_n) = (SRType_LSL, 0);
   5139                 shift_t = SRType_LSL;
   5140                 shift_n = 0;
   5141 
   5142                 // if t == 15 || m == 15 then UNPREDICTABLE;
   5143                 if ((t == 15) || (m == 15))
   5144                     return false;
   5145 
   5146                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   5147                 if (wback && ((n == 15) || (n == t)))
   5148                     return false;
   5149 
   5150                 break;
   5151 
   5152             default:
   5153                 return false;
   5154         }
   5155 
   5156         uint32_t Rm = ReadCoreReg (m, &success);
   5157         if (!success)
   5158             return false;
   5159 
   5160         uint32_t Rn = ReadCoreReg (n, &success);
   5161         if (!success)
   5162             return false;
   5163 
   5164         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   5165         uint32_t offset = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   5166         if (!success)
   5167             return false;
   5168 
   5169         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   5170         addr_t offset_addr;
   5171         if (add)
   5172             offset_addr = Rn + offset;
   5173         else
   5174             offset_addr = Rn - offset;
   5175 
   5176         // address = if index then offset_addr else R[n];
   5177         addr_t address;
   5178         if (index)
   5179             address = offset_addr;
   5180         else
   5181             address = Rn;
   5182 
   5183         EmulateInstruction::Context context;
   5184         context.type = eContextRegisterStore;
   5185         RegisterInfo base_reg;
   5186         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   5187         RegisterInfo offset_reg;
   5188         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   5189 
   5190         // if UnalignedSupport() || address<0> == '0' then
   5191         if (UnalignedSupport() || BitIsClear (address, 0))
   5192         {
   5193             // MemU[address,2] = R[t]<15:0>;
   5194             uint32_t Rt = ReadCoreReg (t, &success);
   5195             if (!success)
   5196                 return false;
   5197 
   5198             EmulateInstruction::Context context;
   5199             context.type = eContextRegisterStore;
   5200             RegisterInfo base_reg;
   5201             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   5202             RegisterInfo offset_reg;
   5203             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   5204             RegisterInfo data_reg;
   5205             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   5206             context.SetRegisterToRegisterPlusIndirectOffset (base_reg, offset_reg, data_reg);
   5207 
   5208             if (!MemUWrite (context, address, Bits32 (Rt, 15, 0), 2))
   5209                 return false;
   5210         }
   5211         else // Can only occur before ARMv7
   5212         {
   5213             // MemU[address,2] = bits(16) UNKNOWN;
   5214         }
   5215 
   5216         // if wback then R[n] = offset_addr;
   5217         if (wback)
   5218         {
   5219             context.type = eContextAdjustBaseRegister;
   5220             context.SetAddress (offset_addr);
   5221             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   5222                 return false;
   5223         }
   5224     }
   5225 
   5226     return true;
   5227 }
   5228 
   5229 // Add with Carry (immediate) adds an immediate value and the carry flag value to a register value,
   5230 // and writes the result to the destination register.  It can optionally update the condition flags
   5231 // based on the result.
   5232 bool
   5233 EmulateInstructionARM::EmulateADCImm (const uint32_t opcode, const ARMEncoding encoding)
   5234 {
   5235 #if 0
   5236     // ARM pseudo code...
   5237     if ConditionPassed() then
   5238         EncodingSpecificOperations();
   5239         (result, carry, overflow) = AddWithCarry(R[n], imm32, APSR.C);
   5240         if d == 15 then         // Can only occur for ARM encoding
   5241             ALUWritePC(result); // setflags is always FALSE here
   5242         else
   5243             R[d] = result;
   5244             if setflags then
   5245                 APSR.N = result<31>;
   5246                 APSR.Z = IsZeroBit(result);
   5247                 APSR.C = carry;
   5248                 APSR.V = overflow;
   5249 #endif
   5250 
   5251     bool success = false;
   5252 
   5253     if (ConditionPassed(opcode))
   5254     {
   5255         uint32_t Rd, Rn;
   5256         uint32_t imm32; // the immediate value to be added to the value obtained from Rn
   5257         bool setflags;
   5258         switch (encoding)
   5259         {
   5260         case eEncodingT1:
   5261             Rd = Bits32(opcode, 11, 8);
   5262             Rn = Bits32(opcode, 19, 16);
   5263             setflags = BitIsSet(opcode, 20);
   5264             imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   5265             if (BadReg(Rd) || BadReg(Rn))
   5266                 return false;
   5267             break;
   5268         case eEncodingA1:
   5269             Rd = Bits32(opcode, 15, 12);
   5270             Rn = Bits32(opcode, 19, 16);
   5271             setflags = BitIsSet(opcode, 20);
   5272             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   5273 
   5274             if (Rd == 15 && setflags)
   5275                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5276             break;
   5277         default:
   5278             return false;
   5279         }
   5280 
   5281         // Read the first operand.
   5282         int32_t val1 = ReadCoreReg(Rn, &success);
   5283         if (!success)
   5284             return false;
   5285 
   5286         AddWithCarryResult res = AddWithCarry(val1, imm32, APSR_C);
   5287 
   5288         EmulateInstruction::Context context;
   5289         context.type = EmulateInstruction::eContextImmediate;
   5290         context.SetNoArgs ();
   5291 
   5292         if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   5293             return false;
   5294     }
   5295     return true;
   5296 }
   5297 
   5298 // Add with Carry (register) adds a register value, the carry flag value, and an optionally-shifted
   5299 // register value, and writes the result to the destination register.  It can optionally update the
   5300 // condition flags based on the result.
   5301 bool
   5302 EmulateInstructionARM::EmulateADCReg (const uint32_t opcode, const ARMEncoding encoding)
   5303 {
   5304 #if 0
   5305     // ARM pseudo code...
   5306     if ConditionPassed() then
   5307         EncodingSpecificOperations();
   5308         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   5309         (result, carry, overflow) = AddWithCarry(R[n], shifted, APSR.C);
   5310         if d == 15 then         // Can only occur for ARM encoding
   5311             ALUWritePC(result); // setflags is always FALSE here
   5312         else
   5313             R[d] = result;
   5314             if setflags then
   5315                 APSR.N = result<31>;
   5316                 APSR.Z = IsZeroBit(result);
   5317                 APSR.C = carry;
   5318                 APSR.V = overflow;
   5319 #endif
   5320 
   5321     bool success = false;
   5322 
   5323     if (ConditionPassed(opcode))
   5324     {
   5325         uint32_t Rd, Rn, Rm;
   5326         ARM_ShifterType shift_t;
   5327         uint32_t shift_n; // the shift applied to the value read from Rm
   5328         bool setflags;
   5329         switch (encoding)
   5330         {
   5331         case eEncodingT1:
   5332             Rd = Rn = Bits32(opcode, 2, 0);
   5333             Rm = Bits32(opcode, 5, 3);
   5334             setflags = !InITBlock();
   5335             shift_t = SRType_LSL;
   5336             shift_n = 0;
   5337             break;
   5338         case eEncodingT2:
   5339             Rd = Bits32(opcode, 11, 8);
   5340             Rn = Bits32(opcode, 19, 16);
   5341             Rm = Bits32(opcode, 3, 0);
   5342             setflags = BitIsSet(opcode, 20);
   5343             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   5344             if (BadReg(Rd) || BadReg(Rn) || BadReg(Rm))
   5345                 return false;
   5346             break;
   5347         case eEncodingA1:
   5348             Rd = Bits32(opcode, 15, 12);
   5349             Rn = Bits32(opcode, 19, 16);
   5350             Rm = Bits32(opcode, 3, 0);
   5351             setflags = BitIsSet(opcode, 20);
   5352             shift_n = DecodeImmShiftARM(opcode, shift_t);
   5353 
   5354             if (Rd == 15 && setflags)
   5355                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5356             break;
   5357         default:
   5358             return false;
   5359         }
   5360 
   5361         // Read the first operand.
   5362         int32_t val1 = ReadCoreReg(Rn, &success);
   5363         if (!success)
   5364             return false;
   5365 
   5366         // Read the second operand.
   5367         int32_t val2 = ReadCoreReg(Rm, &success);
   5368         if (!success)
   5369             return false;
   5370 
   5371         uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   5372         if (!success)
   5373             return false;
   5374         AddWithCarryResult res = AddWithCarry(val1, shifted, APSR_C);
   5375 
   5376         EmulateInstruction::Context context;
   5377         context.type = EmulateInstruction::eContextImmediate;
   5378         context.SetNoArgs ();
   5379 
   5380         if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   5381             return false;
   5382     }
   5383     return true;
   5384 }
   5385 
   5386 // This instruction adds an immediate value to the PC value to form a PC-relative address,
   5387 // and writes the result to the destination register.
   5388 bool
   5389 EmulateInstructionARM::EmulateADR (const uint32_t opcode, const ARMEncoding encoding)
   5390 {
   5391 #if 0
   5392     // ARM pseudo code...
   5393     if ConditionPassed() then
   5394         EncodingSpecificOperations();
   5395         result = if add then (Align(PC,4) + imm32) else (Align(PC,4) - imm32);
   5396         if d == 15 then         // Can only occur for ARM encodings
   5397             ALUWritePC(result);
   5398         else
   5399             R[d] = result;
   5400 #endif
   5401 
   5402     bool success = false;
   5403 
   5404     if (ConditionPassed(opcode))
   5405     {
   5406         uint32_t Rd;
   5407         uint32_t imm32; // the immediate value to be added/subtracted to/from the PC
   5408         bool add;
   5409         switch (encoding)
   5410         {
   5411         case eEncodingT1:
   5412             Rd = Bits32(opcode, 10, 8);
   5413             imm32 = ThumbImm8Scaled(opcode); // imm32 = ZeroExtend(imm8:'00', 32)
   5414             add = true;
   5415             break;
   5416         case eEncodingT2:
   5417         case eEncodingT3:
   5418             Rd = Bits32(opcode, 11, 8);
   5419             imm32 = ThumbImm12(opcode); // imm32 = ZeroExtend(i:imm3:imm8, 32)
   5420             add = (Bits32(opcode, 24, 21) == 0); // 0b0000 => ADD; 0b0101 => SUB
   5421             if (BadReg(Rd))
   5422                 return false;
   5423             break;
   5424         case eEncodingA1:
   5425         case eEncodingA2:
   5426             Rd = Bits32(opcode, 15, 12);
   5427             imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   5428             add = (Bits32(opcode, 24, 21) == 0x4); // 0b0100 => ADD; 0b0010 => SUB
   5429             break;
   5430         default:
   5431             return false;
   5432         }
   5433 
   5434         // Read the PC value.
   5435         uint32_t pc = ReadCoreReg(PC_REG, &success);
   5436         if (!success)
   5437             return false;
   5438 
   5439         uint32_t result = (add ? Align(pc, 4) + imm32 : Align(pc, 4) - imm32);
   5440 
   5441         EmulateInstruction::Context context;
   5442         context.type = EmulateInstruction::eContextImmediate;
   5443         context.SetNoArgs ();
   5444 
   5445         if (!WriteCoreReg(context, result, Rd))
   5446             return false;
   5447     }
   5448     return true;
   5449 }
   5450 
   5451 // This instruction performs a bitwise AND of a register value and an immediate value, and writes the result
   5452 // to the destination register.  It can optionally update the condition flags based on the result.
   5453 bool
   5454 EmulateInstructionARM::EmulateANDImm (const uint32_t opcode, const ARMEncoding encoding)
   5455 {
   5456 #if 0
   5457     // ARM pseudo code...
   5458     if ConditionPassed() then
   5459         EncodingSpecificOperations();
   5460         result = R[n] AND imm32;
   5461         if d == 15 then         // Can only occur for ARM encoding
   5462             ALUWritePC(result); // setflags is always FALSE here
   5463         else
   5464             R[d] = result;
   5465             if setflags then
   5466                 APSR.N = result<31>;
   5467                 APSR.Z = IsZeroBit(result);
   5468                 APSR.C = carry;
   5469                 // APSR.V unchanged
   5470 #endif
   5471 
   5472     bool success = false;
   5473 
   5474     if (ConditionPassed(opcode))
   5475     {
   5476         uint32_t Rd, Rn;
   5477         uint32_t imm32; // the immediate value to be ANDed to the value obtained from Rn
   5478         bool setflags;
   5479         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   5480         switch (encoding)
   5481         {
   5482         case eEncodingT1:
   5483             Rd = Bits32(opcode, 11, 8);
   5484             Rn = Bits32(opcode, 19, 16);
   5485             setflags = BitIsSet(opcode, 20);
   5486             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   5487             // if Rd == '1111' && S == '1' then SEE TST (immediate);
   5488             if (Rd == 15 && setflags)
   5489                 return EmulateTSTImm(opcode, eEncodingT1);
   5490             if (Rd == 13 || (Rd == 15 && !setflags) || BadReg(Rn))
   5491                 return false;
   5492             break;
   5493         case eEncodingA1:
   5494             Rd = Bits32(opcode, 15, 12);
   5495             Rn = Bits32(opcode, 19, 16);
   5496             setflags = BitIsSet(opcode, 20);
   5497             imm32 = ARMExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   5498 
   5499             if (Rd == 15 && setflags)
   5500                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5501             break;
   5502         default:
   5503             return false;
   5504         }
   5505 
   5506         // Read the first operand.
   5507         uint32_t val1 = ReadCoreReg(Rn, &success);
   5508         if (!success)
   5509             return false;
   5510 
   5511         uint32_t result = val1 & imm32;
   5512 
   5513         EmulateInstruction::Context context;
   5514         context.type = EmulateInstruction::eContextImmediate;
   5515         context.SetNoArgs ();
   5516 
   5517         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   5518             return false;
   5519     }
   5520     return true;
   5521 }
   5522 
   5523 // This instruction performs a bitwise AND of a register value and an optionally-shifted register value,
   5524 // and writes the result to the destination register.  It can optionally update the condition flags
   5525 // based on the result.
   5526 bool
   5527 EmulateInstructionARM::EmulateANDReg (const uint32_t opcode, const ARMEncoding encoding)
   5528 {
   5529 #if 0
   5530     // ARM pseudo code...
   5531     if ConditionPassed() then
   5532         EncodingSpecificOperations();
   5533         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   5534         result = R[n] AND shifted;
   5535         if d == 15 then         // Can only occur for ARM encoding
   5536             ALUWritePC(result); // setflags is always FALSE here
   5537         else
   5538             R[d] = result;
   5539             if setflags then
   5540                 APSR.N = result<31>;
   5541                 APSR.Z = IsZeroBit(result);
   5542                 APSR.C = carry;
   5543                 // APSR.V unchanged
   5544 #endif
   5545 
   5546     bool success = false;
   5547 
   5548     if (ConditionPassed(opcode))
   5549     {
   5550         uint32_t Rd, Rn, Rm;
   5551         ARM_ShifterType shift_t;
   5552         uint32_t shift_n; // the shift applied to the value read from Rm
   5553         bool setflags;
   5554         uint32_t carry;
   5555         switch (encoding)
   5556         {
   5557         case eEncodingT1:
   5558             Rd = Rn = Bits32(opcode, 2, 0);
   5559             Rm = Bits32(opcode, 5, 3);
   5560             setflags = !InITBlock();
   5561             shift_t = SRType_LSL;
   5562             shift_n = 0;
   5563             break;
   5564         case eEncodingT2:
   5565             Rd = Bits32(opcode, 11, 8);
   5566             Rn = Bits32(opcode, 19, 16);
   5567             Rm = Bits32(opcode, 3, 0);
   5568             setflags = BitIsSet(opcode, 20);
   5569             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   5570             // if Rd == '1111' && S == '1' then SEE TST (register);
   5571             if (Rd == 15 && setflags)
   5572                 return EmulateTSTReg(opcode, eEncodingT2);
   5573             if (Rd == 13 || (Rd == 15 && !setflags) || BadReg(Rn) || BadReg(Rm))
   5574                 return false;
   5575             break;
   5576         case eEncodingA1:
   5577             Rd = Bits32(opcode, 15, 12);
   5578             Rn = Bits32(opcode, 19, 16);
   5579             Rm = Bits32(opcode, 3, 0);
   5580             setflags = BitIsSet(opcode, 20);
   5581             shift_n = DecodeImmShiftARM(opcode, shift_t);
   5582 
   5583             if (Rd == 15 && setflags)
   5584                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5585             break;
   5586         default:
   5587             return false;
   5588         }
   5589 
   5590         // Read the first operand.
   5591         uint32_t val1 = ReadCoreReg(Rn, &success);
   5592         if (!success)
   5593             return false;
   5594 
   5595         // Read the second operand.
   5596         uint32_t val2 = ReadCoreReg(Rm, &success);
   5597         if (!success)
   5598             return false;
   5599 
   5600         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   5601         if (!success)
   5602             return false;
   5603         uint32_t result = val1 & shifted;
   5604 
   5605         EmulateInstruction::Context context;
   5606         context.type = EmulateInstruction::eContextImmediate;
   5607         context.SetNoArgs ();
   5608 
   5609         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   5610             return false;
   5611     }
   5612     return true;
   5613 }
   5614 
   5615 // Bitwise Bit Clear (immediate) performs a bitwise AND of a register value and the complement of an
   5616 // immediate value, and writes the result to the destination register.  It can optionally update the
   5617 // condition flags based on the result.
   5618 bool
   5619 EmulateInstructionARM::EmulateBICImm (const uint32_t opcode, const ARMEncoding encoding)
   5620 {
   5621 #if 0
   5622     // ARM pseudo code...
   5623     if ConditionPassed() then
   5624         EncodingSpecificOperations();
   5625         result = R[n] AND NOT(imm32);
   5626         if d == 15 then         // Can only occur for ARM encoding
   5627             ALUWritePC(result); // setflags is always FALSE here
   5628         else
   5629             R[d] = result;
   5630             if setflags then
   5631                 APSR.N = result<31>;
   5632                 APSR.Z = IsZeroBit(result);
   5633                 APSR.C = carry;
   5634                 // APSR.V unchanged
   5635 #endif
   5636 
   5637     bool success = false;
   5638 
   5639     if (ConditionPassed(opcode))
   5640     {
   5641         uint32_t Rd, Rn;
   5642         uint32_t imm32; // the immediate value to be bitwise inverted and ANDed to the value obtained from Rn
   5643         bool setflags;
   5644         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   5645         switch (encoding)
   5646         {
   5647         case eEncodingT1:
   5648             Rd = Bits32(opcode, 11, 8);
   5649             Rn = Bits32(opcode, 19, 16);
   5650             setflags = BitIsSet(opcode, 20);
   5651             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   5652             if (BadReg(Rd) || BadReg(Rn))
   5653                 return false;
   5654             break;
   5655         case eEncodingA1:
   5656             Rd = Bits32(opcode, 15, 12);
   5657             Rn = Bits32(opcode, 19, 16);
   5658             setflags = BitIsSet(opcode, 20);
   5659             imm32 = ARMExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   5660 
   5661             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   5662             if (Rd == 15 && setflags)
   5663                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5664             break;
   5665         default:
   5666             return false;
   5667         }
   5668 
   5669         // Read the first operand.
   5670         uint32_t val1 = ReadCoreReg(Rn, &success);
   5671         if (!success)
   5672             return false;
   5673 
   5674         uint32_t result = val1 & ~imm32;
   5675 
   5676         EmulateInstruction::Context context;
   5677         context.type = EmulateInstruction::eContextImmediate;
   5678         context.SetNoArgs ();
   5679 
   5680         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   5681             return false;
   5682     }
   5683     return true;
   5684 }
   5685 
   5686 // Bitwise Bit Clear (register) performs a bitwise AND of a register value and the complement of an
   5687 // optionally-shifted register value, and writes the result to the destination register.
   5688 // It can optionally update the condition flags based on the result.
   5689 bool
   5690 EmulateInstructionARM::EmulateBICReg (const uint32_t opcode, const ARMEncoding encoding)
   5691 {
   5692 #if 0
   5693     // ARM pseudo code...
   5694     if ConditionPassed() then
   5695         EncodingSpecificOperations();
   5696         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   5697         result = R[n] AND NOT(shifted);
   5698         if d == 15 then         // Can only occur for ARM encoding
   5699             ALUWritePC(result); // setflags is always FALSE here
   5700         else
   5701             R[d] = result;
   5702             if setflags then
   5703                 APSR.N = result<31>;
   5704                 APSR.Z = IsZeroBit(result);
   5705                 APSR.C = carry;
   5706                 // APSR.V unchanged
   5707 #endif
   5708 
   5709     bool success = false;
   5710 
   5711     if (ConditionPassed(opcode))
   5712     {
   5713         uint32_t Rd, Rn, Rm;
   5714         ARM_ShifterType shift_t;
   5715         uint32_t shift_n; // the shift applied to the value read from Rm
   5716         bool setflags;
   5717         uint32_t carry;
   5718         switch (encoding)
   5719         {
   5720         case eEncodingT1:
   5721             Rd = Rn = Bits32(opcode, 2, 0);
   5722             Rm = Bits32(opcode, 5, 3);
   5723             setflags = !InITBlock();
   5724             shift_t = SRType_LSL;
   5725             shift_n = 0;
   5726             break;
   5727         case eEncodingT2:
   5728             Rd = Bits32(opcode, 11, 8);
   5729             Rn = Bits32(opcode, 19, 16);
   5730             Rm = Bits32(opcode, 3, 0);
   5731             setflags = BitIsSet(opcode, 20);
   5732             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   5733             if (BadReg(Rd) || BadReg(Rn) || BadReg(Rm))
   5734                 return false;
   5735             break;
   5736         case eEncodingA1:
   5737             Rd = Bits32(opcode, 15, 12);
   5738             Rn = Bits32(opcode, 19, 16);
   5739             Rm = Bits32(opcode, 3, 0);
   5740             setflags = BitIsSet(opcode, 20);
   5741             shift_n = DecodeImmShiftARM(opcode, shift_t);
   5742 
   5743             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   5744             if (Rd == 15 && setflags)
   5745                 return EmulateSUBSPcLrEtc (opcode, encoding);
   5746             break;
   5747         default:
   5748             return false;
   5749         }
   5750 
   5751         // Read the first operand.
   5752         uint32_t val1 = ReadCoreReg(Rn, &success);
   5753         if (!success)
   5754             return false;
   5755 
   5756         // Read the second operand.
   5757         uint32_t val2 = ReadCoreReg(Rm, &success);
   5758         if (!success)
   5759             return false;
   5760 
   5761         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   5762         if (!success)
   5763             return false;
   5764         uint32_t result = val1 & ~shifted;
   5765 
   5766         EmulateInstruction::Context context;
   5767         context.type = EmulateInstruction::eContextImmediate;
   5768         context.SetNoArgs ();
   5769 
   5770         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   5771             return false;
   5772     }
   5773     return true;
   5774 }
   5775 
   5776 // LDR (immediate, ARM) calculates an address from a base register value and an immediate offset, loads a word
   5777 // from memory, and writes it to a register.  It can use offset, post-indexed, or pre-indexed addressing.
   5778 bool
   5779 EmulateInstructionARM::EmulateLDRImmediateARM (const uint32_t opcode, const ARMEncoding encoding)
   5780 {
   5781 #if 0
   5782     if ConditionPassed() then
   5783         EncodingSpecificOperations();
   5784         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   5785         address = if index then offset_addr else R[n];
   5786         data = MemU[address,4];
   5787         if wback then R[n] = offset_addr;
   5788         if t == 15 then
   5789             if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   5790         elsif UnalignedSupport() || address<1:0> = '00' then
   5791             R[t] = data;
   5792         else // Can only apply before ARMv7
   5793             R[t] = ROR(data, 8*UInt(address<1:0>));
   5794 #endif
   5795 
   5796     bool success = false;
   5797 
   5798     if (ConditionPassed(opcode))
   5799     {
   5800         const uint32_t addr_byte_size = GetAddressByteSize();
   5801 
   5802         uint32_t t;
   5803         uint32_t n;
   5804         uint32_t imm32;
   5805         bool index;
   5806         bool add;
   5807         bool wback;
   5808 
   5809         switch (encoding)
   5810         {
   5811             case eEncodingA1:
   5812                 // if Rn == '1111' then SEE LDR (literal);
   5813                 // if P == '0' && W == '1' then SEE LDRT;
   5814                 // if Rn == '1101' && P == '0' && U == '1' && W == '0' && imm12 == '000000000100' then SEE POP;
   5815                 // t == UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   5816                 t = Bits32 (opcode, 15, 12);
   5817                 n = Bits32 (opcode, 19, 16);
   5818                 imm32 = Bits32 (opcode, 11, 0);
   5819 
   5820                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   5821                 index = BitIsSet (opcode, 24);
   5822                 add = BitIsSet (opcode, 23);
   5823                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   5824 
   5825                 // if wback && n == t then UNPREDICTABLE;
   5826                 if (wback && (n == t))
   5827                     return false;
   5828 
   5829                 break;
   5830 
   5831             default:
   5832                 return false;
   5833         }
   5834 
   5835         addr_t address;
   5836         addr_t offset_addr;
   5837         addr_t base_address = ReadCoreReg (n, &success);
   5838         if (!success)
   5839             return false;
   5840 
   5841         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   5842         if (add)
   5843             offset_addr = base_address + imm32;
   5844         else
   5845             offset_addr = base_address - imm32;
   5846 
   5847         // address = if index then offset_addr else R[n];
   5848         if (index)
   5849             address = offset_addr;
   5850         else
   5851             address = base_address;
   5852 
   5853         // data = MemU[address,4];
   5854 
   5855         RegisterInfo base_reg;
   5856         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   5857 
   5858         EmulateInstruction::Context context;
   5859         context.type = eContextRegisterLoad;
   5860         context.SetRegisterPlusOffset (base_reg, address - base_address);
   5861 
   5862         uint64_t data = MemURead (context, address, addr_byte_size, 0, &success);
   5863         if (!success)
   5864             return false;
   5865 
   5866         // if wback then R[n] = offset_addr;
   5867         if (wback)
   5868         {
   5869             context.type = eContextAdjustBaseRegister;
   5870             context.SetAddress (offset_addr);
   5871             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   5872                 return false;
   5873         }
   5874 
   5875         // if t == 15 then
   5876         if (t == 15)
   5877         {
   5878             // if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   5879             if (BitIsClear (address, 1) && BitIsClear (address, 0))
   5880             {
   5881                 // LoadWritePC (data);
   5882                 context.type = eContextRegisterLoad;
   5883                 context.SetRegisterPlusOffset (base_reg, address - base_address);
   5884                 LoadWritePC (context, data);
   5885             }
   5886             else
   5887                   return false;
   5888         }
   5889         // elsif UnalignedSupport() || address<1:0> = '00' then
   5890         else if (UnalignedSupport() || (BitIsClear (address, 1) && BitIsClear (address, 0)))
   5891         {
   5892             // R[t] = data;
   5893             context.type = eContextRegisterLoad;
   5894             context.SetRegisterPlusOffset (base_reg, address - base_address);
   5895             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   5896                 return false;
   5897         }
   5898         // else // Can only apply before ARMv7
   5899         else
   5900         {
   5901             // R[t] = ROR(data, 8*UInt(address<1:0>));
   5902             data = ROR (data, Bits32 (address, 1, 0), &success);
   5903             if (!success)
   5904                 return false;
   5905             context.type = eContextRegisterLoad;
   5906             context.SetImmediate (data);
   5907             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   5908                 return false;
   5909         }
   5910 
   5911     }
   5912     return true;
   5913 }
   5914 
   5915 // LDR (register) calculates an address from a base register value and an offset register value, loads a word
   5916 // from memory, and writes it to a resgister.  The offset register value can optionally be shifted.
   5917 bool
   5918 EmulateInstructionARM::EmulateLDRRegister (const uint32_t opcode, const ARMEncoding encoding)
   5919 {
   5920 #if 0
   5921     if ConditionPassed() then
   5922         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   5923         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   5924         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   5925         address = if index then offset_addr else R[n];
   5926         data = MemU[address,4];
   5927         if wback then R[n] = offset_addr;
   5928         if t == 15 then
   5929             if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   5930         elsif UnalignedSupport() || address<1:0> = '00' then
   5931             R[t] = data;
   5932         else // Can only apply before ARMv7
   5933             if CurrentInstrSet() == InstrSet_ARM then
   5934                 R[t] = ROR(data, 8*UInt(address<1:0>));
   5935             else
   5936                 R[t] = bits(32) UNKNOWN;
   5937 #endif
   5938 
   5939     bool success = false;
   5940 
   5941     if (ConditionPassed(opcode))
   5942     {
   5943         const uint32_t addr_byte_size = GetAddressByteSize();
   5944 
   5945         uint32_t t;
   5946         uint32_t n;
   5947         uint32_t m;
   5948         bool index;
   5949         bool add;
   5950         bool wback;
   5951         ARM_ShifterType shift_t;
   5952         uint32_t shift_n;
   5953 
   5954         switch (encoding)
   5955         {
   5956             case eEncodingT1:
   5957                 // if CurrentInstrSet() == InstrSet_ThumbEE then SEE "Modified operation in ThumbEE";
   5958                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   5959                 t = Bits32 (opcode, 2, 0);
   5960                 n = Bits32 (opcode, 5, 3);
   5961                 m = Bits32 (opcode, 8, 6);
   5962 
   5963                 // index = TRUE; add = TRUE; wback = FALSE;
   5964                 index = true;
   5965                 add = true;
   5966                 wback = false;
   5967 
   5968                 // (shift_t, shift_n) = (SRType_LSL, 0);
   5969                 shift_t = SRType_LSL;
   5970                 shift_n = 0;
   5971 
   5972                 break;
   5973 
   5974             case eEncodingT2:
   5975                 // if Rn == '1111' then SEE LDR (literal);
   5976                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   5977                 t = Bits32 (opcode, 15, 12);
   5978                 n = Bits32 (opcode, 19, 16);
   5979                 m = Bits32 (opcode, 3, 0);
   5980 
   5981                 // index = TRUE; add = TRUE; wback = FALSE;
   5982                 index = true;
   5983                 add = true;
   5984                 wback = false;
   5985 
   5986                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   5987                 shift_t = SRType_LSL;
   5988                 shift_n = Bits32 (opcode, 5, 4);
   5989 
   5990                 // if BadReg(m) then UNPREDICTABLE;
   5991                 if (BadReg (m))
   5992                     return false;
   5993 
   5994                 // if t == 15 && InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   5995                 if ((t == 15) && InITBlock() && !LastInITBlock())
   5996                     return false;
   5997 
   5998                 break;
   5999 
   6000             case eEncodingA1:
   6001             {
   6002                 // if P == '0' && W == '1' then SEE LDRT;
   6003                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6004                 t = Bits32 (opcode, 15, 12);
   6005                 n = Bits32 (opcode, 19, 16);
   6006                 m = Bits32 (opcode, 3, 0);
   6007 
   6008                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   6009                 index = BitIsSet (opcode, 24);
   6010                 add = BitIsSet (opcode, 23);
   6011                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   6012 
   6013                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   6014                 uint32_t type = Bits32 (opcode, 6, 5);
   6015                 uint32_t imm5 = Bits32 (opcode, 11, 7);
   6016                 shift_n = DecodeImmShift (type, imm5, shift_t);
   6017 
   6018                 // if m == 15 then UNPREDICTABLE;
   6019                 if (m == 15)
   6020                     return false;
   6021 
   6022                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   6023                 if (wback && ((n == 15) || (n == t)))
   6024                     return false;
   6025             }
   6026                 break;
   6027 
   6028 
   6029             default:
   6030                 return false;
   6031         }
   6032 
   6033         uint32_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   6034         if (!success)
   6035             return false;
   6036 
   6037         uint32_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   6038         if (!success)
   6039             return false;
   6040 
   6041         addr_t offset_addr;
   6042         addr_t address;
   6043 
   6044         // offset = Shift(R[m], shift_t, shift_n, APSR.C);   -- Note "The APSR is an application level alias for the CPSR".
   6045         addr_t offset = Shift (Rm, shift_t, shift_n, Bit32 (m_opcode_cpsr, APSR_C), &success);
   6046         if (!success)
   6047             return false;
   6048 
   6049         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   6050         if (add)
   6051             offset_addr = Rn + offset;
   6052         else
   6053             offset_addr = Rn - offset;
   6054 
   6055         // address = if index then offset_addr else R[n];
   6056             if (index)
   6057                 address = offset_addr;
   6058             else
   6059                 address = Rn;
   6060 
   6061         // data = MemU[address,4];
   6062         RegisterInfo base_reg;
   6063         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   6064 
   6065         EmulateInstruction::Context context;
   6066         context.type = eContextRegisterLoad;
   6067         context.SetRegisterPlusOffset (base_reg, address - Rn);
   6068 
   6069         uint64_t data = MemURead (context, address, addr_byte_size, 0, &success);
   6070         if (!success)
   6071             return false;
   6072 
   6073         // if wback then R[n] = offset_addr;
   6074         if (wback)
   6075         {
   6076             context.type = eContextAdjustBaseRegister;
   6077             context.SetAddress (offset_addr);
   6078             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   6079                 return false;
   6080         }
   6081 
   6082         // if t == 15 then
   6083         if (t == 15)
   6084         {
   6085             // if address<1:0> == '00' then LoadWritePC(data); else UNPREDICTABLE;
   6086             if (BitIsClear (address, 1) && BitIsClear (address, 0))
   6087             {
   6088                 context.type = eContextRegisterLoad;
   6089                 context.SetRegisterPlusOffset (base_reg, address - Rn);
   6090                 LoadWritePC (context, data);
   6091             }
   6092             else
   6093                 return false;
   6094         }
   6095         // elsif UnalignedSupport() || address<1:0> = '00' then
   6096         else if (UnalignedSupport () || (BitIsClear (address, 1) && BitIsClear (address, 0)))
   6097         {
   6098             // R[t] = data;
   6099             context.type = eContextRegisterLoad;
   6100             context.SetRegisterPlusOffset (base_reg, address - Rn);
   6101             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6102                 return false;
   6103         }
   6104         else // Can only apply before ARMv7
   6105         {
   6106             // if CurrentInstrSet() == InstrSet_ARM then
   6107             if (CurrentInstrSet () == eModeARM)
   6108             {
   6109                 // R[t] = ROR(data, 8*UInt(address<1:0>));
   6110                 data = ROR (data, Bits32 (address, 1, 0), &success);
   6111                 if (!success)
   6112                     return false;
   6113                 context.type = eContextRegisterLoad;
   6114                 context.SetImmediate (data);
   6115                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6116                     return false;
   6117             }
   6118             else
   6119             {
   6120                 // R[t] = bits(32) UNKNOWN;
   6121                 WriteBits32Unknown (t);
   6122             }
   6123         }
   6124     }
   6125     return true;
   6126 }
   6127 
   6128 // LDRB (immediate, Thumb)
   6129 bool
   6130 EmulateInstructionARM::EmulateLDRBImmediate (const uint32_t opcode, const ARMEncoding encoding)
   6131 {
   6132 #if 0
   6133     if ConditionPassed() then
   6134         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6135         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   6136         address = if index then offset_addr else R[n];
   6137         R[t] = ZeroExtend(MemU[address,1], 32);
   6138         if wback then R[n] = offset_addr;
   6139 #endif
   6140 
   6141     bool success = false;
   6142 
   6143     if (ConditionPassed(opcode))
   6144     {
   6145         uint32_t t;
   6146         uint32_t n;
   6147         uint32_t imm32;
   6148         bool index;
   6149         bool add;
   6150         bool wback;
   6151 
   6152         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6153         switch (encoding)
   6154         {
   6155             case eEncodingT1:
   6156                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm5, 32);
   6157                 t = Bits32 (opcode, 2, 0);
   6158                 n = Bits32 (opcode, 5, 3);
   6159                 imm32 = Bits32 (opcode, 10, 6);
   6160 
   6161                 // index = TRUE; add = TRUE; wback = FALSE;
   6162                 index = true;
   6163                 add = true;
   6164                 wback= false;
   6165 
   6166                 break;
   6167 
   6168             case eEncodingT2:
   6169                 // if Rt == '1111' then SEE PLD;
   6170                 // if Rn == '1111' then SEE LDRB (literal);
   6171                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   6172                 t = Bits32 (opcode, 15, 12);
   6173                 n = Bits32 (opcode, 19, 16);
   6174                 imm32 = Bits32 (opcode, 11, 0);
   6175 
   6176                 // index = TRUE; add = TRUE; wback = FALSE;
   6177                 index = true;
   6178                 add = true;
   6179                 wback = false;
   6180 
   6181                 // if t == 13 then UNPREDICTABLE;
   6182                 if (t == 13)
   6183                     return false;
   6184 
   6185                 break;
   6186 
   6187             case eEncodingT3:
   6188                 // if Rt == '1111' && P == '1' && U == '0' && W == '0' then SEE PLD;
   6189                 // if Rn == '1111' then SEE LDRB (literal);
   6190                 // if P == '1' && U == '1' && W == '0' then SEE LDRBT;
   6191                 // if P == '0' && W == '0' then UNDEFINED;
   6192                 if (BitIsClear (opcode, 10) && BitIsClear (opcode, 8))
   6193                     return false;
   6194 
   6195                   // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   6196                 t = Bits32 (opcode, 15, 12);
   6197                 n = Bits32 (opcode, 19, 16);
   6198                 imm32 = Bits32 (opcode, 7, 0);
   6199 
   6200                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   6201                 index = BitIsSet (opcode, 10);
   6202                 add = BitIsSet (opcode, 9);
   6203                 wback = BitIsSet (opcode, 8);
   6204 
   6205                 // if BadReg(t) || (wback && n == t) then UNPREDICTABLE;
   6206                 if (BadReg (t) || (wback && (n == t)))
   6207                     return false;
   6208 
   6209                 break;
   6210 
   6211             default:
   6212                 return false;
   6213         }
   6214 
   6215         uint32_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   6216         if (!success)
   6217             return false;
   6218 
   6219         addr_t address;
   6220         addr_t offset_addr;
   6221 
   6222         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   6223         if (add)
   6224             offset_addr = Rn + imm32;
   6225         else
   6226             offset_addr = Rn - imm32;
   6227 
   6228         // address = if index then offset_addr else R[n];
   6229         if (index)
   6230             address = offset_addr;
   6231         else
   6232             address = Rn;
   6233 
   6234         // R[t] = ZeroExtend(MemU[address,1], 32);
   6235         RegisterInfo base_reg;
   6236         RegisterInfo data_reg;
   6237         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   6238         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   6239 
   6240         EmulateInstruction::Context context;
   6241         context.type = eContextRegisterLoad;
   6242         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   6243 
   6244         uint64_t data = MemURead (context, address, 1, 0, &success);
   6245         if (!success)
   6246             return false;
   6247 
   6248         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6249             return false;
   6250 
   6251         // if wback then R[n] = offset_addr;
   6252         if (wback)
   6253         {
   6254             context.type = eContextAdjustBaseRegister;
   6255             context.SetAddress (offset_addr);
   6256             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   6257                 return false;
   6258         }
   6259     }
   6260     return true;
   6261 }
   6262 
   6263 // LDRB (literal) calculates an address from the PC value and an immediate offset, loads a byte from memory,
   6264 // zero-extends it to form a 32-bit word and writes it to a register.
   6265 bool
   6266 EmulateInstructionARM::EmulateLDRBLiteral (const uint32_t opcode, const ARMEncoding encoding)
   6267 {
   6268 #if 0
   6269     if ConditionPassed() then
   6270         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   6271         base = Align(PC,4);
   6272         address = if add then (base + imm32) else (base - imm32);
   6273         R[t] = ZeroExtend(MemU[address,1], 32);
   6274 #endif
   6275 
   6276     bool success = false;
   6277 
   6278     if (ConditionPassed(opcode))
   6279     {
   6280         uint32_t t;
   6281         uint32_t imm32;
   6282         bool add;
   6283         switch (encoding)
   6284         {
   6285             case eEncodingT1:
   6286                 // if Rt == '1111' then SEE PLD;
   6287                 // t = UInt(Rt); imm32 = ZeroExtend(imm12, 32); add = (U == '1');
   6288                 t = Bits32 (opcode, 15, 12);
   6289                 imm32 = Bits32 (opcode, 11, 0);
   6290                 add = BitIsSet (opcode, 23);
   6291 
   6292                 // if t == 13 then UNPREDICTABLE;
   6293                 if (t == 13)
   6294                     return false;
   6295 
   6296                 break;
   6297 
   6298             case eEncodingA1:
   6299                 // t == UInt(Rt); imm32 = ZeroExtend(imm12, 32); add = (U == '1');
   6300                 t = Bits32 (opcode, 15, 12);
   6301                 imm32 = Bits32 (opcode, 11, 0);
   6302                 add = BitIsSet (opcode, 23);
   6303 
   6304                 // if t == 15 then UNPREDICTABLE;
   6305                 if (t == 15)
   6306                     return false;
   6307                 break;
   6308 
   6309             default:
   6310                 return false;
   6311         }
   6312 
   6313         // base = Align(PC,4);
   6314         uint32_t pc_val = ReadCoreReg (PC_REG, &success);
   6315         if (!success)
   6316             return false;
   6317 
   6318         uint32_t base = AlignPC (pc_val);
   6319 
   6320         addr_t address;
   6321         // address = if add then (base + imm32) else (base - imm32);
   6322         if (add)
   6323             address = base + imm32;
   6324         else
   6325             address = base - imm32;
   6326 
   6327         // R[t] = ZeroExtend(MemU[address,1], 32);
   6328         EmulateInstruction::Context context;
   6329         context.type = eContextRelativeBranchImmediate;
   6330         context.SetImmediate (address - base);
   6331 
   6332         uint64_t data = MemURead (context, address, 1, 0, &success);
   6333         if (!success)
   6334             return false;
   6335 
   6336         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6337             return false;
   6338     }
   6339     return true;
   6340 }
   6341 
   6342 // LDRB (register) calculates an address from a base register value and an offset rigister value, loads a byte from
   6343 // memory, zero-extends it to form a 32-bit word, and writes it to a register.  The offset register value can
   6344 // optionally be shifted.
   6345 bool
   6346 EmulateInstructionARM::EmulateLDRBRegister (const uint32_t opcode, const ARMEncoding encoding)
   6347 {
   6348 #if 0
   6349     if ConditionPassed() then
   6350         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6351         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   6352         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   6353         address = if index then offset_addr else R[n];
   6354         R[t] = ZeroExtend(MemU[address,1],32);
   6355         if wback then R[n] = offset_addr;
   6356 #endif
   6357 
   6358     bool success = false;
   6359 
   6360     if (ConditionPassed(opcode))
   6361     {
   6362         uint32_t t;
   6363         uint32_t n;
   6364         uint32_t m;
   6365         bool index;
   6366         bool add;
   6367         bool wback;
   6368         ARM_ShifterType shift_t;
   6369         uint32_t shift_n;
   6370 
   6371         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6372         switch (encoding)
   6373         {
   6374             case eEncodingT1:
   6375                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6376                 t = Bits32 (opcode, 2, 0);
   6377                 n = Bits32 (opcode, 5, 3);
   6378                 m = Bits32 (opcode, 8, 6);
   6379 
   6380                 // index = TRUE; add = TRUE; wback = FALSE;
   6381                 index = true;
   6382                 add = true;
   6383                 wback = false;
   6384 
   6385                 // (shift_t, shift_n) = (SRType_LSL, 0);
   6386                 shift_t = SRType_LSL;
   6387                 shift_n = 0;
   6388                 break;
   6389 
   6390             case eEncodingT2:
   6391                 // if Rt == '1111' then SEE PLD;
   6392                 // if Rn == '1111' then SEE LDRB (literal);
   6393                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6394                 t = Bits32 (opcode, 15, 12);
   6395                 n = Bits32 (opcode, 19, 16);
   6396                 m = Bits32 (opcode, 3, 0);
   6397 
   6398                 // index = TRUE; add = TRUE; wback = FALSE;
   6399                 index = true;
   6400                 add = true;
   6401                 wback = false;
   6402 
   6403                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   6404                 shift_t = SRType_LSL;
   6405                 shift_n = Bits32 (opcode, 5, 4);
   6406 
   6407                 // if t == 13 || BadReg(m) then UNPREDICTABLE;
   6408                 if ((t == 13) || BadReg (m))
   6409                     return false;
   6410                 break;
   6411 
   6412             case eEncodingA1:
   6413             {
   6414                 // if P == '0' && W == '1' then SEE LDRBT;
   6415                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6416                 t = Bits32 (opcode, 15, 12);
   6417                 n = Bits32 (opcode, 19, 16);
   6418                 m = Bits32 (opcode, 3, 0);
   6419 
   6420                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   6421                 index = BitIsSet (opcode, 24);
   6422                 add = BitIsSet (opcode, 23);
   6423                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   6424 
   6425                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   6426                 uint32_t type = Bits32 (opcode, 6, 5);
   6427                 uint32_t imm5 = Bits32 (opcode, 11, 7);
   6428                 shift_n = DecodeImmShift (type, imm5, shift_t);
   6429 
   6430                 // if t == 15 || m == 15 then UNPREDICTABLE;
   6431                 if ((t == 15) || (m == 15))
   6432                     return false;
   6433 
   6434                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   6435                 if (wback && ((n == 15) || (n == t)))
   6436                     return false;
   6437             }
   6438                 break;
   6439 
   6440             default:
   6441                 return false;
   6442         }
   6443 
   6444         addr_t offset_addr;
   6445         addr_t address;
   6446 
   6447         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   6448         uint32_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   6449         if (!success)
   6450             return false;
   6451 
   6452         addr_t offset = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   6453         if (!success)
   6454             return false;
   6455 
   6456         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   6457         uint32_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   6458         if (!success)
   6459             return false;
   6460 
   6461         if (add)
   6462             offset_addr = Rn + offset;
   6463         else
   6464             offset_addr = Rn - offset;
   6465 
   6466         // address = if index then offset_addr else R[n];
   6467         if (index)
   6468             address = offset_addr;
   6469         else
   6470             address = Rn;
   6471 
   6472         // R[t] = ZeroExtend(MemU[address,1],32);
   6473         RegisterInfo base_reg;
   6474         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   6475 
   6476         EmulateInstruction::Context context;
   6477         context.type = eContextRegisterLoad;
   6478         context.SetRegisterPlusOffset (base_reg, address - Rn);
   6479 
   6480         uint64_t data = MemURead (context, address, 1, 0, &success);
   6481         if (!success)
   6482             return false;
   6483 
   6484         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6485             return false;
   6486 
   6487         // if wback then R[n] = offset_addr;
   6488         if (wback)
   6489         {
   6490             context.type = eContextAdjustBaseRegister;
   6491             context.SetAddress (offset_addr);
   6492             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   6493                 return false;
   6494         }
   6495     }
   6496     return true;
   6497 }
   6498 
   6499 // LDRH (immediate, Thumb) calculates an address from a base register value and an immediate offset, loads a
   6500 // halfword from memory, zero-extends it to form a 32-bit word, and writes it to a register.  It can use offset,
   6501 // post-indexed, or pre-indexed addressing.
   6502 bool
   6503 EmulateInstructionARM::EmulateLDRHImmediate (const uint32_t opcode, const ARMEncoding encoding)
   6504 {
   6505 #if 0
   6506     if ConditionPassed() then
   6507         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6508         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   6509         address = if index then offset_addr else R[n];
   6510         data = MemU[address,2];
   6511         if wback then R[n] = offset_addr;
   6512         if UnalignedSupport() || address<0> = '0' then
   6513             R[t] = ZeroExtend(data, 32);
   6514         else // Can only apply before ARMv7
   6515             R[t] = bits(32) UNKNOWN;
   6516 #endif
   6517 
   6518 
   6519     bool success = false;
   6520 
   6521     if (ConditionPassed(opcode))
   6522     {
   6523         uint32_t t;
   6524         uint32_t n;
   6525         uint32_t imm32;
   6526         bool index;
   6527         bool add;
   6528         bool wback;
   6529 
   6530         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6531         switch (encoding)
   6532         {
   6533             case eEncodingT1:
   6534                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm5:'0', 32);
   6535                 t = Bits32 (opcode, 2, 0);
   6536                 n = Bits32 (opcode, 5, 3);
   6537                 imm32 = Bits32 (opcode, 10, 6) << 1;
   6538 
   6539                 // index = TRUE; add = TRUE; wback = FALSE;
   6540                 index = true;
   6541                 add = true;
   6542                 wback = false;
   6543 
   6544                 break;
   6545 
   6546             case eEncodingT2:
   6547                 // if Rt == '1111' then SEE "Unallocated memory hints";
   6548                 // if Rn == '1111' then SEE LDRH (literal);
   6549                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   6550                 t = Bits32 (opcode, 15, 12);
   6551                 n = Bits32 (opcode, 19, 16);
   6552                 imm32 = Bits32 (opcode, 11, 0);
   6553 
   6554                 // index = TRUE; add = TRUE; wback = FALSE;
   6555                 index = true;
   6556                 add = true;
   6557                 wback = false;
   6558 
   6559                 // if t == 13 then UNPREDICTABLE;
   6560                 if (t == 13)
   6561                     return false;
   6562                 break;
   6563 
   6564             case eEncodingT3:
   6565                 // if Rn == '1111' then SEE LDRH (literal);
   6566                 // if Rt == '1111' && P == '1' && U == '0' && W == '0' then SEE "Unallocated memory hints";
   6567                 // if P == '1' && U == '1' && W == '0' then SEE LDRHT;
   6568                 // if P == '0' && W == '0' then UNDEFINED;
   6569                 if (BitIsClear (opcode, 10) && BitIsClear (opcode, 8))
   6570                     return false;
   6571 
   6572                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   6573                 t = Bits32 (opcode, 15, 12);
   6574                 n = Bits32 (opcode, 19, 16);
   6575                 imm32 = Bits32 (opcode, 7, 0);
   6576 
   6577                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   6578                 index = BitIsSet (opcode, 10);
   6579                 add = BitIsSet (opcode, 9);
   6580                 wback = BitIsSet (opcode, 8);
   6581 
   6582                 // if BadReg(t) || (wback && n == t) then UNPREDICTABLE;
   6583                 if (BadReg (t) || (wback && (n == t)))
   6584                     return false;
   6585                 break;
   6586 
   6587             default:
   6588                 return false;
   6589         }
   6590 
   6591         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   6592         uint32_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   6593         if (!success)
   6594             return false;
   6595 
   6596         addr_t offset_addr;
   6597         addr_t address;
   6598 
   6599         if (add)
   6600             offset_addr = Rn + imm32;
   6601         else
   6602             offset_addr = Rn - imm32;
   6603 
   6604         // address = if index then offset_addr else R[n];
   6605         if (index)
   6606             address = offset_addr;
   6607         else
   6608             address = Rn;
   6609 
   6610         // data = MemU[address,2];
   6611         RegisterInfo base_reg;
   6612         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   6613 
   6614         EmulateInstruction::Context context;
   6615         context.type = eContextRegisterLoad;
   6616         context.SetRegisterPlusOffset (base_reg, address - Rn);
   6617 
   6618         uint64_t data = MemURead (context, address, 2, 0, &success);
   6619         if (!success)
   6620             return false;
   6621 
   6622         // if wback then R[n] = offset_addr;
   6623         if (wback)
   6624         {
   6625             context.type = eContextAdjustBaseRegister;
   6626             context.SetAddress (offset_addr);
   6627             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   6628                 return false;
   6629         }
   6630 
   6631         // if UnalignedSupport() || address<0> = '0' then
   6632         if (UnalignedSupport () || BitIsClear (address, 0))
   6633         {
   6634             // R[t] = ZeroExtend(data, 32);
   6635             context.type = eContextRegisterLoad;
   6636             context.SetRegisterPlusOffset (base_reg, address - Rn);
   6637             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6638                 return false;
   6639         }
   6640         else // Can only apply before ARMv7
   6641         {
   6642             // R[t] = bits(32) UNKNOWN;
   6643             WriteBits32Unknown (t);
   6644         }
   6645     }
   6646     return true;
   6647 }
   6648 
   6649 // LDRH (literal) caculates an address from the PC value and an immediate offset, loads a halfword from memory,
   6650 // zero-extends it to form a 32-bit word, and writes it to a register.
   6651 bool
   6652 EmulateInstructionARM::EmulateLDRHLiteral (const uint32_t opcode, const ARMEncoding encoding)
   6653 {
   6654 #if 0
   6655     if ConditionPassed() then
   6656         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   6657         base = Align(PC,4);
   6658         address = if add then (base + imm32) else (base - imm32);
   6659         data = MemU[address,2];
   6660         if UnalignedSupport() || address<0> = '0' then
   6661             R[t] = ZeroExtend(data, 32);
   6662         else // Can only apply before ARMv7
   6663             R[t] = bits(32) UNKNOWN;
   6664 #endif
   6665 
   6666     bool success = false;
   6667 
   6668     if (ConditionPassed(opcode))
   6669     {
   6670         uint32_t t;
   6671         uint32_t imm32;
   6672         bool add;
   6673 
   6674         // EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   6675         switch (encoding)
   6676         {
   6677             case eEncodingT1:
   6678                 // if Rt == '1111' then SEE "Unallocated memory hints";
   6679                 // t = UInt(Rt); imm32 = ZeroExtend(imm12, 32); add = (U == '1');
   6680                 t = Bits32 (opcode, 15, 12);
   6681                 imm32 = Bits32 (opcode, 11, 0);
   6682                 add = BitIsSet (opcode, 23);
   6683 
   6684                 // if t == 13 then UNPREDICTABLE;
   6685                 if (t == 13)
   6686                     return false;
   6687 
   6688                 break;
   6689 
   6690             case eEncodingA1:
   6691             {
   6692                 uint32_t imm4H = Bits32 (opcode, 11, 8);
   6693                 uint32_t imm4L = Bits32 (opcode, 3, 0);
   6694 
   6695                 // t == UInt(Rt); imm32 = ZeroExtend(imm4H:imm4L, 32); add = (U == '1');
   6696                 t = Bits32 (opcode, 15, 12);
   6697                 imm32 = (imm4H << 4) | imm4L;
   6698                 add = BitIsSet (opcode, 23);
   6699 
   6700                 // if t == 15 then UNPREDICTABLE;
   6701                 if (t == 15)
   6702                     return false;
   6703                 break;
   6704             }
   6705 
   6706             default:
   6707                 return false;
   6708         }
   6709 
   6710         // base = Align(PC,4);
   6711         uint64_t pc_value = ReadCoreReg (PC_REG, &success);
   6712         if (!success)
   6713             return false;
   6714 
   6715         addr_t base = AlignPC (pc_value);
   6716         addr_t address;
   6717 
   6718         // address = if add then (base + imm32) else (base - imm32);
   6719         if (add)
   6720             address = base + imm32;
   6721         else
   6722             address = base - imm32;
   6723 
   6724         // data = MemU[address,2];
   6725         RegisterInfo base_reg;
   6726         GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, base_reg);
   6727 
   6728         EmulateInstruction::Context context;
   6729         context.type = eContextRegisterLoad;
   6730         context.SetRegisterPlusOffset (base_reg, address - base);
   6731 
   6732         uint64_t data = MemURead (context, address, 2, 0, &success);
   6733         if (!success)
   6734             return false;
   6735 
   6736 
   6737         // if UnalignedSupport() || address<0> = '0' then
   6738         if (UnalignedSupport () || BitIsClear (address, 0))
   6739         {
   6740             // R[t] = ZeroExtend(data, 32);
   6741             context.type = eContextRegisterLoad;
   6742             context.SetRegisterPlusOffset (base_reg, address - base);
   6743             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6744                 return false;
   6745 
   6746         }
   6747         else // Can only apply before ARMv7
   6748         {
   6749             // R[t] = bits(32) UNKNOWN;
   6750             WriteBits32Unknown (t);
   6751         }
   6752     }
   6753     return true;
   6754 }
   6755 
   6756 // LDRH (literal) calculates an address from a base register value and an offset register value, loads a halfword
   6757 // from memory, zero-extends it to form a 32-bit word, and writes it to a register.  The offset register value can
   6758 // be shifted left by 0, 1, 2, or 3 bits.
   6759 bool
   6760 EmulateInstructionARM::EmulateLDRHRegister (const uint32_t opcode, const ARMEncoding encoding)
   6761 {
   6762 #if 0
   6763     if ConditionPassed() then
   6764         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6765         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   6766         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   6767         address = if index then offset_addr else R[n];
   6768         data = MemU[address,2];
   6769         if wback then R[n] = offset_addr;
   6770         if UnalignedSupport() || address<0> = '0' then
   6771             R[t] = ZeroExtend(data, 32);
   6772         else // Can only apply before ARMv7
   6773             R[t] = bits(32) UNKNOWN;
   6774 #endif
   6775 
   6776     bool success = false;
   6777 
   6778     if (ConditionPassed(opcode))
   6779     {
   6780         uint32_t t;
   6781         uint32_t n;
   6782         uint32_t m;
   6783         bool index;
   6784         bool add;
   6785         bool wback;
   6786         ARM_ShifterType shift_t;
   6787         uint32_t shift_n;
   6788 
   6789         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6790         switch (encoding)
   6791         {
   6792             case eEncodingT1:
   6793                 // if CurrentInstrSet() == InstrSet_ThumbEE then SEE "Modified operation in ThumbEE";
   6794                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6795                 t = Bits32 (opcode, 2, 0);
   6796                 n = Bits32 (opcode, 5, 3);
   6797                 m = Bits32 (opcode, 8, 6);
   6798 
   6799                 // index = TRUE; add = TRUE; wback = FALSE;
   6800                 index = true;
   6801                 add = true;
   6802                 wback = false;
   6803 
   6804                 // (shift_t, shift_n) = (SRType_LSL, 0);
   6805                 shift_t = SRType_LSL;
   6806                 shift_n = 0;
   6807 
   6808                 break;
   6809 
   6810             case eEncodingT2:
   6811                 // if Rn == '1111' then SEE LDRH (literal);
   6812                 // if Rt == '1111' then SEE "Unallocated memory hints";
   6813                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6814                 t = Bits32 (opcode, 15, 12);
   6815                 n = Bits32 (opcode, 19, 16);
   6816                 m = Bits32 (opcode, 3, 0);
   6817 
   6818                 // index = TRUE; add = TRUE; wback = FALSE;
   6819                 index = true;
   6820                 add = true;
   6821                 wback = false;
   6822 
   6823                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   6824                 shift_t = SRType_LSL;
   6825                 shift_n = Bits32 (opcode, 5, 4);
   6826 
   6827                 // if t == 13 || BadReg(m) then UNPREDICTABLE;
   6828                 if ((t == 13) || BadReg (m))
   6829                     return false;
   6830                 break;
   6831 
   6832             case eEncodingA1:
   6833                 // if P == '0' && W == '1' then SEE LDRHT;
   6834                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   6835                 t = Bits32 (opcode, 15, 12);
   6836                 n = Bits32 (opcode, 19, 16);
   6837                 m = Bits32 (opcode, 3, 0);
   6838 
   6839                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   6840                 index = BitIsSet (opcode, 24);
   6841                 add = BitIsSet (opcode, 23);
   6842                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   6843 
   6844                 // (shift_t, shift_n) = (SRType_LSL, 0);
   6845                 shift_t = SRType_LSL;
   6846                 shift_n = 0;
   6847 
   6848                 // if t == 15 || m == 15 then UNPREDICTABLE;
   6849                 if ((t == 15) || (m == 15))
   6850                     return false;
   6851 
   6852                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   6853                 if (wback && ((n == 15) || (n == t)))
   6854                     return false;
   6855 
   6856                 break;
   6857 
   6858             default:
   6859                 return false;
   6860         }
   6861 
   6862         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   6863 
   6864         uint64_t Rm  = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   6865         if (!success)
   6866             return false;
   6867 
   6868         addr_t offset = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   6869         if (!success)
   6870             return false;
   6871 
   6872         addr_t offset_addr;
   6873         addr_t address;
   6874 
   6875         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   6876         uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   6877         if (!success)
   6878             return false;
   6879 
   6880         if (add)
   6881             offset_addr = Rn + offset;
   6882         else
   6883             offset_addr = Rn - offset;
   6884 
   6885         // address = if index then offset_addr else R[n];
   6886         if (index)
   6887             address = offset_addr;
   6888         else
   6889             address = Rn;
   6890 
   6891         // data = MemU[address,2];
   6892         RegisterInfo base_reg;
   6893         RegisterInfo offset_reg;
   6894         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   6895         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   6896 
   6897         EmulateInstruction::Context context;
   6898         context.type = eContextRegisterLoad;
   6899         context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   6900         uint64_t data = MemURead (context, address, 2, 0, &success);
   6901         if (!success)
   6902             return false;
   6903 
   6904         // if wback then R[n] = offset_addr;
   6905         if (wback)
   6906         {
   6907             context.type = eContextAdjustBaseRegister;
   6908             context.SetAddress (offset_addr);
   6909             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   6910                 return false;
   6911         }
   6912 
   6913         // if UnalignedSupport() || address<0> = '0' then
   6914         if (UnalignedSupport() || BitIsClear (address, 0))
   6915         {
   6916             // R[t] = ZeroExtend(data, 32);
   6917             context.type = eContextRegisterLoad;
   6918             context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   6919             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   6920                 return false;
   6921         }
   6922         else // Can only apply before ARMv7
   6923         {
   6924             // R[t] = bits(32) UNKNOWN;
   6925             WriteBits32Unknown (t);
   6926         }
   6927     }
   6928     return true;
   6929 }
   6930 
   6931 // LDRSB (immediate) calculates an address from a base register value and an immediate offset, loads a byte from
   6932 // memory, sign-extends it to form a 32-bit word, and writes it to a register.  It can use offset, post-indexed,
   6933 // or pre-indexed addressing.
   6934 bool
   6935 EmulateInstructionARM::EmulateLDRSBImmediate (const uint32_t opcode, const ARMEncoding encoding)
   6936 {
   6937 #if 0
   6938     if ConditionPassed() then
   6939         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6940         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   6941         address = if index then offset_addr else R[n];
   6942         R[t] = SignExtend(MemU[address,1], 32);
   6943         if wback then R[n] = offset_addr;
   6944 #endif
   6945 
   6946     bool success = false;
   6947 
   6948     if (ConditionPassed(opcode))
   6949     {
   6950         uint32_t t;
   6951         uint32_t n;
   6952         uint32_t imm32;
   6953         bool index;
   6954         bool add;
   6955         bool wback;
   6956 
   6957         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   6958         switch (encoding)
   6959         {
   6960             case eEncodingT1:
   6961                 // if Rt == '1111' then SEE PLI;
   6962                 // if Rn == '1111' then SEE LDRSB (literal);
   6963                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   6964                 t = Bits32 (opcode, 15, 12);
   6965                 n = Bits32 (opcode, 19, 16);
   6966                 imm32 = Bits32 (opcode, 11, 0);
   6967 
   6968                 // index = TRUE; add = TRUE; wback = FALSE;
   6969                 index = true;
   6970                 add = true;
   6971                 wback = false;
   6972 
   6973                 // if t == 13 then UNPREDICTABLE;
   6974                 if (t == 13)
   6975                     return false;
   6976 
   6977                 break;
   6978 
   6979             case eEncodingT2:
   6980                 // if Rt == '1111' && P == '1' && U == '0' && W == '0' then SEE PLI;
   6981                 // if Rn == '1111' then SEE LDRSB (literal);
   6982                 // if P == '1' && U == '1' && W == '0' then SEE LDRSBT;
   6983                 // if P == '0' && W == '0' then UNDEFINED;
   6984                 if (BitIsClear (opcode, 10) && BitIsClear (opcode, 8))
   6985                     return false;
   6986 
   6987                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   6988                 t = Bits32 (opcode, 15, 12);
   6989                 n = Bits32 (opcode, 19, 16);
   6990                 imm32 = Bits32 (opcode, 7, 0);
   6991 
   6992                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   6993                 index = BitIsSet (opcode, 10);
   6994                 add = BitIsSet (opcode, 9);
   6995                 wback = BitIsSet (opcode, 8);
   6996 
   6997                 // if BadReg(t) || (wback && n == t) then UNPREDICTABLE;
   6998                   if (((t == 13) || ((t == 15)
   6999                                      && (BitIsClear (opcode, 10) || BitIsSet (opcode, 9) || BitIsSet (opcode, 8))))
   7000                       || (wback && (n == t)))
   7001                     return false;
   7002 
   7003                 break;
   7004 
   7005             case eEncodingA1:
   7006             {
   7007                 // if Rn == '1111' then SEE LDRSB (literal);
   7008                 // if P == '0' && W == '1' then SEE LDRSBT;
   7009                 // t == UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32);
   7010                 t = Bits32 (opcode, 15, 12);
   7011                 n = Bits32 (opcode, 19, 16);
   7012 
   7013                 uint32_t imm4H = Bits32 (opcode, 11, 8);
   7014                 uint32_t imm4L = Bits32 (opcode, 3, 0);
   7015                 imm32 = (imm4H << 4) | imm4L;
   7016 
   7017                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   7018                 index = BitIsSet (opcode, 24);
   7019                 add = BitIsSet (opcode, 23);
   7020                 wback = (BitIsClear (opcode, 24) || BitIsSet (opcode, 21));
   7021 
   7022                 // if t == 15 || (wback && n == t) then UNPREDICTABLE;
   7023                 if ((t == 15) || (wback && (n == t)))
   7024                     return false;
   7025 
   7026                 break;
   7027             }
   7028 
   7029             default:
   7030                 return false;
   7031         }
   7032 
   7033         uint64_t Rn = ReadCoreReg (n, &success);
   7034         if (!success)
   7035             return false;
   7036 
   7037         addr_t offset_addr;
   7038         addr_t address;
   7039 
   7040         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   7041         if (add)
   7042             offset_addr = Rn + imm32;
   7043         else
   7044             offset_addr = Rn - imm32;
   7045 
   7046         // address = if index then offset_addr else R[n];
   7047         if (index)
   7048             address = offset_addr;
   7049         else
   7050             address = Rn;
   7051 
   7052         // R[t] = SignExtend(MemU[address,1], 32);
   7053         RegisterInfo base_reg;
   7054         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   7055 
   7056         EmulateInstruction::Context context;
   7057         context.type = eContextRegisterLoad;
   7058         context.SetRegisterPlusOffset (base_reg, address - Rn);
   7059 
   7060         uint64_t unsigned_data = MemURead (context, address, 1, 0, &success);
   7061         if (!success)
   7062             return false;
   7063 
   7064         int64_t signed_data = llvm::SignExtend64<8>(unsigned_data);
   7065         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7066             return false;
   7067 
   7068         // if wback then R[n] = offset_addr;
   7069         if (wback)
   7070         {
   7071             context.type = eContextAdjustBaseRegister;
   7072             context.SetAddress (offset_addr);
   7073             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   7074                 return false;
   7075         }
   7076     }
   7077 
   7078     return true;
   7079 }
   7080 
   7081 // LDRSB (literal) calculates an address from the PC value and an immediate offset, loads a byte from memory,
   7082 // sign-extends it to form a 32-bit word, and writes tit to a register.
   7083 bool
   7084 EmulateInstructionARM::EmulateLDRSBLiteral (const uint32_t opcode, const ARMEncoding encoding)
   7085 {
   7086 #if 0
   7087     if ConditionPassed() then
   7088         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   7089         base = Align(PC,4);
   7090         address = if add then (base + imm32) else (base - imm32);
   7091         R[t] = SignExtend(MemU[address,1], 32);
   7092 #endif
   7093 
   7094     bool success = false;
   7095 
   7096     if (ConditionPassed(opcode))
   7097     {
   7098         uint32_t t;
   7099         uint32_t imm32;
   7100         bool add;
   7101 
   7102         // EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   7103         switch (encoding)
   7104         {
   7105             case eEncodingT1:
   7106                 // if Rt == '1111' then SEE PLI;
   7107                 // t = UInt(Rt); imm32 = ZeroExtend(imm12, 32); add = (U == '1');
   7108                 t = Bits32 (opcode, 15, 12);
   7109                 imm32 = Bits32 (opcode, 11, 0);
   7110                 add = BitIsSet (opcode, 23);
   7111 
   7112                 // if t == 13 then UNPREDICTABLE;
   7113                 if (t == 13)
   7114                     return false;
   7115 
   7116                 break;
   7117 
   7118             case eEncodingA1:
   7119             {
   7120                 // t == UInt(Rt); imm32 = ZeroExtend(imm4H:imm4L, 32); add = (U == '1');
   7121                 t = Bits32 (opcode, 15, 12);
   7122                 uint32_t imm4H = Bits32 (opcode, 11, 8);
   7123                 uint32_t imm4L = Bits32 (opcode, 3, 0);
   7124                 imm32 = (imm4H << 4) | imm4L;
   7125                 add = BitIsSet (opcode, 23);
   7126 
   7127                 // if t == 15 then UNPREDICTABLE;
   7128                 if (t == 15)
   7129                     return false;
   7130 
   7131                 break;
   7132             }
   7133 
   7134             default:
   7135                 return false;
   7136         }
   7137 
   7138         // base = Align(PC,4);
   7139         uint64_t pc_value = ReadCoreReg (PC_REG, &success);
   7140         if (!success)
   7141             return false;
   7142         uint64_t base = AlignPC (pc_value);
   7143 
   7144         // address = if add then (base + imm32) else (base - imm32);
   7145         addr_t address;
   7146         if (add)
   7147             address = base + imm32;
   7148         else
   7149             address = base - imm32;
   7150 
   7151         // R[t] = SignExtend(MemU[address,1], 32);
   7152         RegisterInfo base_reg;
   7153         GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, base_reg);
   7154 
   7155         EmulateInstruction::Context context;
   7156         context.type = eContextRegisterLoad;
   7157         context.SetRegisterPlusOffset (base_reg, address - base);
   7158 
   7159         uint64_t unsigned_data = MemURead (context, address, 1, 0, &success);
   7160         if (!success)
   7161             return false;
   7162 
   7163         int64_t signed_data = llvm::SignExtend64<8>(unsigned_data);
   7164         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7165             return false;
   7166     }
   7167     return true;
   7168 }
   7169 
   7170 // LDRSB (register) calculates an address from a base register value and an offset register value, loadsa byte from
   7171 // memory, sign-extends it to form a 32-bit word, and writes it to a register.  The offset register value can be
   7172 // shifted left by 0, 1, 2, or 3 bits.
   7173 bool
   7174 EmulateInstructionARM::EmulateLDRSBRegister (const uint32_t opcode, const ARMEncoding encoding)
   7175 {
   7176 #if 0
   7177     if ConditionPassed() then
   7178         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7179         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   7180         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   7181         address = if index then offset_addr else R[n];
   7182         R[t] = SignExtend(MemU[address,1], 32);
   7183         if wback then R[n] = offset_addr;
   7184 #endif
   7185 
   7186     bool success = false;
   7187 
   7188     if (ConditionPassed(opcode))
   7189     {
   7190         uint32_t t;
   7191         uint32_t n;
   7192         uint32_t m;
   7193         bool index;
   7194         bool add;
   7195         bool wback;
   7196         ARM_ShifterType shift_t;
   7197         uint32_t shift_n;
   7198 
   7199         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7200         switch (encoding)
   7201         {
   7202             case eEncodingT1:
   7203                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7204                 t = Bits32 (opcode, 2, 0);
   7205                 n = Bits32 (opcode, 5, 3);
   7206                 m = Bits32 (opcode, 8, 6);
   7207 
   7208                 // index = TRUE; add = TRUE; wback = FALSE;
   7209                 index = true;
   7210                 add = true;
   7211                 wback = false;
   7212 
   7213                 // (shift_t, shift_n) = (SRType_LSL, 0);
   7214                 shift_t = SRType_LSL;
   7215                 shift_n = 0;
   7216 
   7217                 break;
   7218 
   7219             case eEncodingT2:
   7220                 // if Rt == '1111' then SEE PLI;
   7221                 // if Rn == '1111' then SEE LDRSB (literal);
   7222                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7223                 t = Bits32 (opcode, 15, 12);
   7224                 n = Bits32 (opcode, 19, 16);
   7225                 m = Bits32 (opcode, 3, 0);
   7226 
   7227                 // index = TRUE; add = TRUE; wback = FALSE;
   7228                 index = true;
   7229                 add = true;
   7230                 wback = false;
   7231 
   7232                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   7233                 shift_t = SRType_LSL;
   7234                 shift_n = Bits32 (opcode, 5, 4);
   7235 
   7236                 // if t == 13 || BadReg(m) then UNPREDICTABLE;
   7237                 if ((t == 13) || BadReg (m))
   7238                     return false;
   7239                 break;
   7240 
   7241             case eEncodingA1:
   7242                 // if P == '0' && W == '1' then SEE LDRSBT;
   7243                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7244                 t = Bits32 (opcode, 15, 12);
   7245                 n = Bits32 (opcode, 19, 16);
   7246                 m = Bits32 (opcode, 3, 0);
   7247 
   7248                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   7249                 index = BitIsSet (opcode, 24);
   7250                 add = BitIsSet (opcode, 23);
   7251                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   7252 
   7253                 // (shift_t, shift_n) = (SRType_LSL, 0);
   7254                 shift_t = SRType_LSL;
   7255                 shift_n = 0;
   7256 
   7257                 // if t == 15 || m == 15 then UNPREDICTABLE;
   7258                 if ((t == 15) || (m == 15))
   7259                     return false;
   7260 
   7261                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   7262                 if (wback && ((n == 15) || (n == t)))
   7263                     return false;
   7264                 break;
   7265 
   7266             default:
   7267                 return false;
   7268         }
   7269 
   7270         uint64_t Rm =  ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   7271         if (!success)
   7272             return false;
   7273 
   7274         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   7275         addr_t offset = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   7276         if (!success)
   7277             return false;
   7278 
   7279         addr_t offset_addr;
   7280         addr_t address;
   7281 
   7282         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   7283         uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   7284         if (!success)
   7285             return false;
   7286 
   7287         if (add)
   7288             offset_addr = Rn + offset;
   7289         else
   7290             offset_addr = Rn - offset;
   7291 
   7292         // address = if index then offset_addr else R[n];
   7293         if (index)
   7294             address = offset_addr;
   7295         else
   7296             address = Rn;
   7297 
   7298         // R[t] = SignExtend(MemU[address,1], 32);
   7299         RegisterInfo base_reg;
   7300         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   7301         RegisterInfo offset_reg;
   7302         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   7303 
   7304         EmulateInstruction::Context context;
   7305         context.type = eContextRegisterLoad;
   7306         context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   7307 
   7308         uint64_t unsigned_data = MemURead (context, address, 1, 0, &success);
   7309         if (!success)
   7310             return false;
   7311 
   7312         int64_t signed_data = llvm::SignExtend64<8>(unsigned_data);
   7313         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7314             return false;
   7315 
   7316         // if wback then R[n] = offset_addr;
   7317         if (wback)
   7318         {
   7319             context.type = eContextAdjustBaseRegister;
   7320             context.SetAddress (offset_addr);
   7321             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   7322                 return false;
   7323         }
   7324     }
   7325     return true;
   7326 }
   7327 
   7328 // LDRSH (immediate) calculates an address from a base register value and an immediate offset, loads a halfword from
   7329 // memory, sign-extends it to form a 32-bit word, and writes it to a register.  It can use offset, post-indexed, or
   7330 // pre-indexed addressing.
   7331 bool
   7332 EmulateInstructionARM::EmulateLDRSHImmediate (const uint32_t opcode, const ARMEncoding encoding)
   7333 {
   7334 #if 0
   7335     if ConditionPassed() then
   7336         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7337         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   7338         address = if index then offset_addr else R[n];
   7339         data = MemU[address,2];
   7340         if wback then R[n] = offset_addr;
   7341         if UnalignedSupport() || address<0> = '0' then
   7342             R[t] = SignExtend(data, 32);
   7343         else // Can only apply before ARMv7
   7344             R[t] = bits(32) UNKNOWN;
   7345 #endif
   7346 
   7347     bool success = false;
   7348 
   7349     if (ConditionPassed(opcode))
   7350     {
   7351         uint32_t t;
   7352         uint32_t n;
   7353         uint32_t imm32;
   7354         bool index;
   7355         bool add;
   7356         bool wback;
   7357 
   7358         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7359         switch (encoding)
   7360         {
   7361             case eEncodingT1:
   7362                 // if Rn == '1111' then SEE LDRSH (literal);
   7363                 // if Rt == '1111' then SEE "Unallocated memory hints";
   7364                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   7365                 t = Bits32 (opcode, 15, 12);
   7366                 n = Bits32 (opcode, 19, 16);
   7367                 imm32 = Bits32 (opcode, 11, 0);
   7368 
   7369                 // index = TRUE; add = TRUE; wback = FALSE;
   7370                 index = true;
   7371                 add = true;
   7372                 wback = false;
   7373 
   7374                 // if t == 13 then UNPREDICTABLE;
   7375                 if (t == 13)
   7376                     return false;
   7377 
   7378                 break;
   7379 
   7380             case eEncodingT2:
   7381                 // if Rn == '1111' then SEE LDRSH (literal);
   7382                 // if Rt == '1111' && P == '1' && U == '0' && W == '0' then SEE "Unallocated memory hints";
   7383                 // if P == '1' && U == '1' && W == '0' then SEE LDRSHT;
   7384                 // if P == '0' && W == '0' then UNDEFINED;
   7385                   if (BitIsClear (opcode, 10) && BitIsClear (opcode, 8))
   7386                   return false;
   7387 
   7388                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8, 32);
   7389                 t = Bits32 (opcode, 15, 12);
   7390                 n = Bits32 (opcode, 19, 16);
   7391                 imm32 = Bits32 (opcode, 7, 0);
   7392 
   7393                 // index = (P == '1'); add = (U == '1'); wback = (W == '1');
   7394                 index = BitIsSet (opcode, 10);
   7395                 add = BitIsSet (opcode, 9);
   7396                 wback = BitIsSet (opcode, 8);
   7397 
   7398                 // if BadReg(t) || (wback && n == t) then UNPREDICTABLE;
   7399                 if (BadReg (t) || (wback && (n == t)))
   7400                     return false;
   7401 
   7402                 break;
   7403 
   7404             case eEncodingA1:
   7405             {
   7406                 // if Rn == '1111' then SEE LDRSH (literal);
   7407                 // if P == '0' && W == '1' then SEE LDRSHT;
   7408                 // t == UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32);
   7409                 t = Bits32 (opcode, 15, 12);
   7410                 n = Bits32 (opcode, 19, 16);
   7411                 uint32_t imm4H = Bits32 (opcode, 11,8);
   7412                 uint32_t imm4L = Bits32 (opcode, 3, 0);
   7413                 imm32 = (imm4H << 4) | imm4L;
   7414 
   7415                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   7416                 index = BitIsSet (opcode, 24);
   7417                 add = BitIsSet (opcode, 23);
   7418                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   7419 
   7420                 // if t == 15 || (wback && n == t) then UNPREDICTABLE;
   7421                 if ((t == 15) || (wback && (n == t)))
   7422                     return false;
   7423 
   7424                 break;
   7425             }
   7426 
   7427             default:
   7428                 return false;
   7429         }
   7430 
   7431         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   7432         uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   7433         if (!success)
   7434             return false;
   7435 
   7436         addr_t offset_addr;
   7437         if (add)
   7438             offset_addr = Rn + imm32;
   7439         else
   7440             offset_addr = Rn - imm32;
   7441 
   7442         // address = if index then offset_addr else R[n];
   7443         addr_t address;
   7444         if (index)
   7445             address = offset_addr;
   7446         else
   7447             address = Rn;
   7448 
   7449         // data = MemU[address,2];
   7450         RegisterInfo base_reg;
   7451         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   7452 
   7453         EmulateInstruction::Context context;
   7454         context.type = eContextRegisterLoad;
   7455         context.SetRegisterPlusOffset (base_reg, address - Rn);
   7456 
   7457         uint64_t data = MemURead (context, address, 2, 0, &success);
   7458         if (!success)
   7459             return false;
   7460 
   7461         // if wback then R[n] = offset_addr;
   7462         if (wback)
   7463         {
   7464             context.type = eContextAdjustBaseRegister;
   7465             context.SetAddress (offset_addr);
   7466             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   7467                 return false;
   7468         }
   7469 
   7470         // if UnalignedSupport() || address<0> = '0' then
   7471         if (UnalignedSupport() || BitIsClear (address, 0))
   7472         {
   7473             // R[t] = SignExtend(data, 32);
   7474             int64_t signed_data = llvm::SignExtend64<16>(data);
   7475             context.type = eContextRegisterLoad;
   7476             context.SetRegisterPlusOffset (base_reg, address - Rn);
   7477             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7478                 return false;
   7479         }
   7480         else // Can only apply before ARMv7
   7481         {
   7482             // R[t] = bits(32) UNKNOWN;
   7483             WriteBits32Unknown (t);
   7484         }
   7485     }
   7486     return true;
   7487 }
   7488 
   7489 // LDRSH (literal) calculates an address from the PC value and an immediate offset, loads a halfword from memory,
   7490 // sign-extends it to from a 32-bit word, and writes it to a register.
   7491 bool
   7492 EmulateInstructionARM::EmulateLDRSHLiteral (const uint32_t opcode, const ARMEncoding encoding)
   7493 {
   7494 #if 0
   7495     if ConditionPassed() then
   7496         EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   7497         base = Align(PC,4);
   7498         address = if add then (base + imm32) else (base - imm32);
   7499         data = MemU[address,2];
   7500         if UnalignedSupport() || address<0> = '0' then
   7501             R[t] = SignExtend(data, 32);
   7502         else // Can only apply before ARMv7
   7503             R[t] = bits(32) UNKNOWN;
   7504 #endif
   7505 
   7506     bool success = false;
   7507 
   7508     if (ConditionPassed(opcode))
   7509     {
   7510         uint32_t t;
   7511         uint32_t imm32;
   7512         bool add;
   7513 
   7514         // EncodingSpecificOperations(); NullCheckIfThumbEE(15);
   7515         switch (encoding)
   7516         {
   7517             case eEncodingT1:
   7518                 // if Rt == '1111' then SEE "Unallocated memory hints";
   7519                 // t = UInt(Rt); imm32 = ZeroExtend(imm12, 32); add = (U == '1');
   7520                 t = Bits32  (opcode, 15, 12);
   7521                 imm32 = Bits32 (opcode, 11, 0);
   7522                 add = BitIsSet (opcode, 23);
   7523 
   7524                 // if t == 13 then UNPREDICTABLE;
   7525                 if (t == 13)
   7526                     return false;
   7527 
   7528                 break;
   7529 
   7530             case eEncodingA1:
   7531             {
   7532                 // t == UInt(Rt); imm32 = ZeroExtend(imm4H:imm4L, 32); add = (U == '1');
   7533                 t = Bits32 (opcode, 15, 12);
   7534                 uint32_t imm4H = Bits32 (opcode, 11, 8);
   7535                 uint32_t imm4L = Bits32 (opcode, 3, 0);
   7536                 imm32 = (imm4H << 4) | imm4L;
   7537                 add = BitIsSet (opcode, 23);
   7538 
   7539                 // if t == 15 then UNPREDICTABLE;
   7540                 if (t == 15)
   7541                     return false;
   7542 
   7543                 break;
   7544             }
   7545             default:
   7546                 return false;
   7547         }
   7548 
   7549         // base = Align(PC,4);
   7550         uint64_t pc_value = ReadCoreReg (PC_REG, &success);
   7551         if (!success)
   7552             return false;
   7553 
   7554         uint64_t base = AlignPC (pc_value);
   7555 
   7556         addr_t address;
   7557         // address = if add then (base + imm32) else (base - imm32);
   7558         if (add)
   7559             address = base + imm32;
   7560         else
   7561             address = base - imm32;
   7562 
   7563         // data = MemU[address,2];
   7564         RegisterInfo base_reg;
   7565         GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, base_reg);
   7566 
   7567         EmulateInstruction::Context context;
   7568         context.type = eContextRegisterLoad;
   7569         context.SetRegisterPlusOffset (base_reg, imm32);
   7570 
   7571         uint64_t data = MemURead (context, address, 2, 0, &success);
   7572         if (!success)
   7573             return false;
   7574 
   7575         // if UnalignedSupport() || address<0> = '0' then
   7576         if (UnalignedSupport() || BitIsClear (address, 0))
   7577         {
   7578             // R[t] = SignExtend(data, 32);
   7579             int64_t signed_data = llvm::SignExtend64<16>(data);
   7580             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7581                 return false;
   7582         }
   7583         else // Can only apply before ARMv7
   7584         {
   7585             // R[t] = bits(32) UNKNOWN;
   7586             WriteBits32Unknown (t);
   7587         }
   7588     }
   7589     return true;
   7590 }
   7591 
   7592 // LDRSH (register) calculates an address from a base register value and an offset register value, loads a halfword
   7593 // from memory, sign-extends it to form a 32-bit word, and writes it to a register.  The offset register value can be
   7594 // shifted left by 0, 1, 2, or 3 bits.
   7595 bool
   7596 EmulateInstructionARM::EmulateLDRSHRegister (const uint32_t opcode, const ARMEncoding encoding)
   7597 {
   7598 #if 0
   7599     if ConditionPassed() then
   7600         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7601         offset = Shift(R[m], shift_t, shift_n, APSR.C);
   7602         offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   7603         address = if index then offset_addr else R[n];
   7604         data = MemU[address,2];
   7605         if wback then R[n] = offset_addr;
   7606         if UnalignedSupport() || address<0> = '0' then
   7607             R[t] = SignExtend(data, 32);
   7608         else // Can only apply before ARMv7
   7609             R[t] = bits(32) UNKNOWN;
   7610 #endif
   7611 
   7612     bool success = false;
   7613 
   7614     if (ConditionPassed(opcode))
   7615     {
   7616         uint32_t t;
   7617         uint32_t n;
   7618         uint32_t m;
   7619         bool index;
   7620         bool add;
   7621         bool wback;
   7622         ARM_ShifterType shift_t;
   7623         uint32_t shift_n;
   7624 
   7625         // EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   7626         switch (encoding)
   7627         {
   7628             case eEncodingT1:
   7629                 // if CurrentInstrSet() == InstrSet_ThumbEE then SEE "Modified operation in ThumbEE";
   7630                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7631                 t = Bits32 (opcode, 2, 0);
   7632                 n = Bits32 (opcode, 5, 3);
   7633                 m = Bits32 (opcode, 8, 6);
   7634 
   7635                 // index = TRUE; add = TRUE; wback = FALSE;
   7636                 index = true;
   7637                 add = true;
   7638                 wback = false;
   7639 
   7640                 // (shift_t, shift_n) = (SRType_LSL, 0);
   7641                 shift_t = SRType_LSL;
   7642                 shift_n = 0;
   7643 
   7644                 break;
   7645 
   7646             case eEncodingT2:
   7647                 // if Rn == '1111' then SEE LDRSH (literal);
   7648                 // if Rt == '1111' then SEE "Unallocated memory hints";
   7649                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7650                 t = Bits32 (opcode, 15, 12);
   7651                 n = Bits32 (opcode, 19, 16);
   7652                 m = Bits32 (opcode, 3, 0);
   7653 
   7654                 // index = TRUE; add = TRUE; wback = FALSE;
   7655                 index = true;
   7656                 add = true;
   7657                 wback = false;
   7658 
   7659                 // (shift_t, shift_n) = (SRType_LSL, UInt(imm2));
   7660                 shift_t = SRType_LSL;
   7661                 shift_n = Bits32 (opcode, 5, 4);
   7662 
   7663                 // if t == 13 || BadReg(m) then UNPREDICTABLE;
   7664                 if ((t == 13) || BadReg (m))
   7665                     return false;
   7666 
   7667                 break;
   7668 
   7669             case eEncodingA1:
   7670                 // if P == '0' && W == '1' then SEE LDRSHT;
   7671                 // t = UInt(Rt); n = UInt(Rn); m = UInt(Rm);
   7672                 t = Bits32 (opcode, 15, 12);
   7673                 n = Bits32 (opcode, 19, 16);
   7674                 m = Bits32 (opcode, 3, 0);
   7675 
   7676                 // index = (P == '1');	add = (U == '1');	wback = (P == '0') || (W == '1');
   7677                 index = BitIsSet (opcode, 24);
   7678                 add = BitIsSet (opcode, 23);
   7679                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   7680 
   7681                 // (shift_t, shift_n) = (SRType_LSL, 0);
   7682                 shift_t = SRType_LSL;
   7683                 shift_n = 0;
   7684 
   7685                 // if t == 15 || m == 15 then UNPREDICTABLE;
   7686                 if ((t == 15) || (m == 15))
   7687                     return false;
   7688 
   7689                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   7690                 if (wback && ((n == 15) || (n == t)))
   7691                     return false;
   7692 
   7693                 break;
   7694 
   7695             default:
   7696                 return false;
   7697         }
   7698 
   7699         uint64_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   7700         if (!success)
   7701             return false;
   7702 
   7703         uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   7704         if (!success)
   7705             return false;
   7706 
   7707         // offset = Shift(R[m], shift_t, shift_n, APSR.C);
   7708         addr_t offset = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   7709         if (!success)
   7710             return false;
   7711 
   7712         addr_t offset_addr;
   7713         addr_t address;
   7714 
   7715         // offset_addr = if add then (R[n] + offset) else (R[n] - offset);
   7716         if (add)
   7717             offset_addr = Rn + offset;
   7718         else
   7719             offset_addr = Rn - offset;
   7720 
   7721         // address = if index then offset_addr else R[n];
   7722         if (index)
   7723             address = offset_addr;
   7724         else
   7725             address = Rn;
   7726 
   7727         // data = MemU[address,2];
   7728         RegisterInfo base_reg;
   7729         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   7730 
   7731         RegisterInfo offset_reg;
   7732         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   7733 
   7734         EmulateInstruction::Context context;
   7735         context.type = eContextRegisterLoad;
   7736         context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   7737 
   7738         uint64_t data = MemURead (context, address, 2, 0, &success);
   7739         if (!success)
   7740             return false;
   7741 
   7742         // if wback then R[n] = offset_addr;
   7743         if (wback)
   7744         {
   7745             context.type = eContextAdjustBaseRegister;
   7746             context.SetAddress (offset_addr);
   7747             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   7748                 return false;
   7749         }
   7750 
   7751         // if UnalignedSupport() || address<0> = '0' then
   7752         if (UnalignedSupport() || BitIsClear (address, 0))
   7753         {
   7754             // R[t] = SignExtend(data, 32);
   7755             context.type = eContextRegisterLoad;
   7756             context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   7757 
   7758             int64_t signed_data = llvm::SignExtend64<16>(data);
   7759             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, (uint64_t) signed_data))
   7760                 return false;
   7761         }
   7762         else // Can only apply before ARMv7
   7763         {
   7764             // R[t] = bits(32) UNKNOWN;
   7765             WriteBits32Unknown (t);
   7766         }
   7767     }
   7768     return true;
   7769 }
   7770 
   7771 // SXTB extracts an 8-bit value from a register, sign-extends it to 32 bits, and writes the result to the destination
   7772 // register.  You can specifiy a rotation by 0, 8, 16, or 24 bits before extracting the 8-bit value.
   7773 bool
   7774 EmulateInstructionARM::EmulateSXTB (const uint32_t opcode, const ARMEncoding encoding)
   7775 {
   7776 #if 0
   7777     if ConditionPassed() then
   7778         EncodingSpecificOperations();
   7779         rotated = ROR(R[m], rotation);
   7780         R[d] = SignExtend(rotated<7:0>, 32);
   7781 #endif
   7782 
   7783     bool success = false;
   7784 
   7785     if (ConditionPassed(opcode))
   7786     {
   7787         uint32_t d;
   7788         uint32_t m;
   7789         uint32_t rotation;
   7790 
   7791         // EncodingSpecificOperations();
   7792         switch (encoding)
   7793         {
   7794             case eEncodingT1:
   7795                 // d = UInt(Rd); m = UInt(Rm); rotation = 0;
   7796                 d = Bits32 (opcode, 2, 0);
   7797                 m = Bits32 (opcode, 5, 3);
   7798                 rotation = 0;
   7799 
   7800                 break;
   7801 
   7802             case eEncodingT2:
   7803                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7804                 d = Bits32 (opcode, 11, 8);
   7805                 m = Bits32 (opcode, 3, 0);
   7806                 rotation = Bits32 (opcode, 5, 4) << 3;
   7807 
   7808                 // if BadReg(d) || BadReg(m) then UNPREDICTABLE;
   7809                 if (BadReg (d) || BadReg (m))
   7810                     return false;
   7811 
   7812                 break;
   7813 
   7814             case eEncodingA1:
   7815                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7816                 d = Bits32 (opcode, 15, 12);
   7817                 m = Bits32 (opcode, 3, 0);
   7818                 rotation = Bits32 (opcode, 11, 10) << 3;
   7819 
   7820                 // if d == 15 || m == 15 then UNPREDICTABLE;
   7821                 if ((d == 15) || (m == 15))
   7822                     return false;
   7823 
   7824                 break;
   7825 
   7826             default:
   7827                 return false;
   7828         }
   7829 
   7830         uint64_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   7831         if (!success)
   7832             return false;
   7833 
   7834         // rotated = ROR(R[m], rotation);
   7835         uint64_t rotated = ROR (Rm, rotation, &success);
   7836         if (!success)
   7837             return false;
   7838 
   7839         // R[d] = SignExtend(rotated<7:0>, 32);
   7840         int64_t data = llvm::SignExtend64<8>(rotated);
   7841 
   7842         RegisterInfo source_reg;
   7843         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, source_reg);
   7844 
   7845         EmulateInstruction::Context context;
   7846         context.type = eContextRegisterLoad;
   7847         context.SetRegister (source_reg);
   7848 
   7849         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, (uint64_t) data))
   7850             return false;
   7851     }
   7852     return true;
   7853 }
   7854 
   7855 // SXTH extracts a 16-bit value from a register, sign-extends it to 32 bits, and writes the result to the destination
   7856 // register.  You can specify a rotation by 0, 8, 16, or 24 bits before extracting the 16-bit value.
   7857 bool
   7858 EmulateInstructionARM::EmulateSXTH (const uint32_t opcode, const ARMEncoding encoding)
   7859 {
   7860 #if 0
   7861     if ConditionPassed() then
   7862         EncodingSpecificOperations();
   7863         rotated = ROR(R[m], rotation);
   7864         R[d] = SignExtend(rotated<15:0>, 32);
   7865 #endif
   7866 
   7867     bool success = false;
   7868 
   7869     if (ConditionPassed(opcode))
   7870     {
   7871         uint32_t d;
   7872         uint32_t m;
   7873         uint32_t rotation;
   7874 
   7875         // EncodingSpecificOperations();
   7876         switch (encoding)
   7877         {
   7878             case eEncodingT1:
   7879                 // d = UInt(Rd); m = UInt(Rm); rotation = 0;
   7880                 d = Bits32 (opcode, 2, 0);
   7881                 m = Bits32 (opcode, 5, 3);
   7882                 rotation = 0;
   7883 
   7884                 break;
   7885 
   7886             case eEncodingT2:
   7887                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7888                 d = Bits32 (opcode, 11, 8);
   7889                 m = Bits32 (opcode, 3, 0);
   7890                 rotation = Bits32 (opcode, 5, 4) << 3;
   7891 
   7892                 // if BadReg(d) || BadReg(m) then UNPREDICTABLE;
   7893                 if (BadReg (d) || BadReg (m))
   7894                     return false;
   7895 
   7896                 break;
   7897 
   7898             case eEncodingA1:
   7899                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7900                 d = Bits32 (opcode, 15, 12);
   7901                 m = Bits32 (opcode, 3, 0);
   7902                 rotation = Bits32 (opcode, 11, 10) << 3;
   7903 
   7904                 // if d == 15 || m == 15 then UNPREDICTABLE;
   7905                 if ((d == 15) || (m == 15))
   7906                     return false;
   7907 
   7908                 break;
   7909 
   7910             default:
   7911                 return false;
   7912         }
   7913 
   7914         uint64_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   7915         if (!success)
   7916             return false;
   7917 
   7918         // rotated = ROR(R[m], rotation);
   7919         uint64_t rotated = ROR (Rm, rotation, &success);
   7920         if (!success)
   7921             return false;
   7922 
   7923         // R[d] = SignExtend(rotated<15:0>, 32);
   7924         RegisterInfo source_reg;
   7925         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, source_reg);
   7926 
   7927         EmulateInstruction::Context context;
   7928         context.type = eContextRegisterLoad;
   7929         context.SetRegister (source_reg);
   7930 
   7931         int64_t data = llvm::SignExtend64<16> (rotated);
   7932         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, (uint64_t) data))
   7933             return false;
   7934     }
   7935 
   7936     return true;
   7937 }
   7938 
   7939 // UXTB extracts an 8-bit value from a register, zero-extneds it to 32 bits, and writes the result to the destination
   7940 // register.  You can specify a rotation by 0, 8, 16, or 24 bits before extracting the 8-bit value.
   7941 bool
   7942 EmulateInstructionARM::EmulateUXTB (const uint32_t opcode, const ARMEncoding encoding)
   7943 {
   7944 #if 0
   7945     if ConditionPassed() then
   7946         EncodingSpecificOperations();
   7947         rotated = ROR(R[m], rotation);
   7948         R[d] = ZeroExtend(rotated<7:0>, 32);
   7949 #endif
   7950 
   7951     bool success = false;
   7952 
   7953     if (ConditionPassed(opcode))
   7954     {
   7955         uint32_t d;
   7956         uint32_t m;
   7957         uint32_t rotation;
   7958 
   7959         // EncodingSpecificOperations();
   7960         switch (encoding)
   7961         {
   7962             case eEncodingT1:
   7963                 // d = UInt(Rd); m = UInt(Rm); rotation = 0;
   7964                 d = Bits32 (opcode, 2, 0);
   7965                 m = Bits32 (opcode, 5, 3);
   7966                 rotation = 0;
   7967 
   7968                 break;
   7969 
   7970             case eEncodingT2:
   7971                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7972                 d = Bits32 (opcode, 11, 8);
   7973                 m = Bits32 (opcode, 3, 0);
   7974                   rotation = Bits32 (opcode, 5, 4) << 3;
   7975 
   7976                 // if BadReg(d) || BadReg(m) then UNPREDICTABLE;
   7977                 if (BadReg (d) || BadReg (m))
   7978                   return false;
   7979 
   7980                 break;
   7981 
   7982             case eEncodingA1:
   7983                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   7984                 d = Bits32 (opcode, 15, 12);
   7985                 m = Bits32 (opcode, 3, 0);
   7986                 rotation = Bits32 (opcode, 11, 10) << 3;
   7987 
   7988                 // if d == 15 || m == 15 then UNPREDICTABLE;
   7989                 if ((d == 15) || (m == 15))
   7990                     return false;
   7991 
   7992                 break;
   7993 
   7994             default:
   7995                 return false;
   7996         }
   7997 
   7998         uint64_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   7999         if (!success)
   8000             return false;
   8001 
   8002         // rotated = ROR(R[m], rotation);
   8003         uint64_t rotated = ROR (Rm, rotation, &success);
   8004         if (!success)
   8005             return false;
   8006 
   8007         // R[d] = ZeroExtend(rotated<7:0>, 32);
   8008         RegisterInfo source_reg;
   8009         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, source_reg);
   8010 
   8011         EmulateInstruction::Context context;
   8012         context.type = eContextRegisterLoad;
   8013         context.SetRegister (source_reg);
   8014 
   8015         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, Bits32 (rotated, 7, 0)))
   8016             return false;
   8017     }
   8018     return true;
   8019 }
   8020 
   8021 // UXTH extracts a 16-bit value from a register, zero-extends it to 32 bits, and writes the result to the destination
   8022 // register.  You can specify a rotation by 0, 8, 16, or 24 bits before extracting the 16-bit value.
   8023 bool
   8024 EmulateInstructionARM::EmulateUXTH (const uint32_t opcode, const ARMEncoding encoding)
   8025 {
   8026 #if 0
   8027     if ConditionPassed() then
   8028         EncodingSpecificOperations();
   8029         rotated = ROR(R[m], rotation);
   8030         R[d] = ZeroExtend(rotated<15:0>, 32);
   8031 #endif
   8032 
   8033     bool success = false;
   8034 
   8035     if (ConditionPassed(opcode))
   8036     {
   8037         uint32_t d;
   8038         uint32_t m;
   8039         uint32_t rotation;
   8040 
   8041         switch (encoding)
   8042         {
   8043             case eEncodingT1:
   8044                 // d = UInt(Rd); m = UInt(Rm); rotation = 0;
   8045                 d = Bits32 (opcode, 2, 0);
   8046                 m = Bits32 (opcode, 5, 3);
   8047                 rotation = 0;
   8048 
   8049                 break;
   8050 
   8051             case eEncodingT2:
   8052                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   8053                 d = Bits32 (opcode, 11, 8);
   8054                 m = Bits32 (opcode, 3, 0);
   8055                 rotation = Bits32 (opcode, 5, 4) << 3;
   8056 
   8057                 // if BadReg(d) || BadReg(m) then UNPREDICTABLE;
   8058                 if (BadReg (d) || BadReg (m))
   8059                   return false;
   8060 
   8061                 break;
   8062 
   8063             case eEncodingA1:
   8064                 // d = UInt(Rd); m = UInt(Rm); rotation = UInt(rotate:'000');
   8065                 d = Bits32 (opcode, 15, 12);
   8066                 m = Bits32 (opcode, 3, 0);
   8067                 rotation = Bits32 (opcode, 11, 10) << 3;
   8068 
   8069                 // if d == 15 || m == 15 then UNPREDICTABLE;
   8070                 if ((d == 15) || (m == 15))
   8071                     return false;
   8072 
   8073                 break;
   8074 
   8075             default:
   8076                 return false;
   8077         }
   8078 
   8079         uint64_t Rm = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + m, 0, &success);
   8080         if (!success)
   8081             return false;
   8082 
   8083         // rotated = ROR(R[m], rotation);
   8084         uint64_t rotated = ROR (Rm, rotation, &success);
   8085         if (!success)
   8086             return false;
   8087 
   8088         // R[d] = ZeroExtend(rotated<15:0>, 32);
   8089         RegisterInfo source_reg;
   8090         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, source_reg);
   8091 
   8092         EmulateInstruction::Context context;
   8093         context.type = eContextRegisterLoad;
   8094         context.SetRegister (source_reg);
   8095 
   8096         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, Bits32 (rotated, 15, 0)))
   8097             return false;
   8098     }
   8099     return true;
   8100 }
   8101 
   8102 // RFE (Return From Exception) loads the PC and the CPSR from the word at the specified address and the following
   8103 // word respectively.
   8104 bool
   8105 EmulateInstructionARM::EmulateRFE (const uint32_t opcode, const ARMEncoding encoding)
   8106 {
   8107 #if 0
   8108     if ConditionPassed() then
   8109         EncodingSpecificOperations();
   8110         if !CurrentModeIsPrivileged() || CurrentInstrSet() == InstrSet_ThumbEE then
   8111             UNPREDICTABLE;
   8112         else
   8113             address = if increment then R[n] else R[n]-8;
   8114             if wordhigher then address = address+4;
   8115             CPSRWriteByInstr(MemA[address+4,4], '1111', TRUE);
   8116             BranchWritePC(MemA[address,4]);
   8117             if wback then R[n] = if increment then R[n]+8 else R[n]-8;
   8118 #endif
   8119 
   8120     bool success = false;
   8121 
   8122     if (ConditionPassed(opcode))
   8123     {
   8124         uint32_t n;
   8125         bool wback;
   8126         bool increment;
   8127         bool wordhigher;
   8128 
   8129         // EncodingSpecificOperations();
   8130         switch (encoding)
   8131         {
   8132             case eEncodingT1:
   8133                 // n = UInt(Rn); wback = (W == '1'); increment = FALSE; wordhigher = FALSE;
   8134                 n = Bits32 (opcode, 19, 16);
   8135                 wback = BitIsSet (opcode, 21);
   8136                 increment = false;
   8137                 wordhigher = false;
   8138 
   8139                 // if n == 15 then UNPREDICTABLE;
   8140                 if (n == 15)
   8141                     return false;
   8142 
   8143                 // if InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   8144                 if (InITBlock() && !LastInITBlock())
   8145                     return false;
   8146 
   8147                 break;
   8148 
   8149             case eEncodingT2:
   8150                 // n = UInt(Rn); wback = (W == '1'); increment = TRUE; wordhigher = FALSE;
   8151                 n = Bits32 (opcode, 19, 16);
   8152                 wback = BitIsSet (opcode, 21);
   8153                 increment = true;
   8154                 wordhigher = false;
   8155 
   8156                 // if n == 15 then UNPREDICTABLE;
   8157                 if (n == 15)
   8158                     return false;
   8159 
   8160                 // if InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   8161                 if (InITBlock() && !LastInITBlock())
   8162                     return false;
   8163 
   8164                 break;
   8165 
   8166             case eEncodingA1:
   8167                 // n = UInt(Rn);
   8168                 n = Bits32 (opcode, 19, 16);
   8169 
   8170                 // wback = (W == '1'); inc = (U == '1'); wordhigher = (P == U);
   8171                 wback = BitIsSet (opcode, 21);
   8172                 increment = BitIsSet (opcode, 23);
   8173                 wordhigher = (Bit32 (opcode, 24) == Bit32 (opcode, 23));
   8174 
   8175                 // if n == 15 then UNPREDICTABLE;
   8176                 if (n == 15)
   8177                     return false;
   8178 
   8179                 break;
   8180 
   8181             default:
   8182                 return false;
   8183         }
   8184 
   8185         // if !CurrentModeIsPrivileged() || CurrentInstrSet() == InstrSet_ThumbEE then
   8186         if (!CurrentModeIsPrivileged ())
   8187             // UNPREDICTABLE;
   8188             return false;
   8189         else
   8190         {
   8191             uint64_t Rn = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + n, 0, &success);
   8192             if (!success)
   8193                 return false;
   8194 
   8195             addr_t address;
   8196             // address = if increment then R[n] else R[n]-8;
   8197             if (increment)
   8198                 address = Rn;
   8199             else
   8200                 address = Rn - 8;
   8201 
   8202             // if wordhigher then address = address+4;
   8203             if (wordhigher)
   8204                 address = address + 4;
   8205 
   8206             // CPSRWriteByInstr(MemA[address+4,4], '1111', TRUE);
   8207             RegisterInfo base_reg;
   8208             GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   8209 
   8210             EmulateInstruction::Context context;
   8211             context.type = eContextReturnFromException;
   8212             context.SetRegisterPlusOffset (base_reg, address - Rn);
   8213 
   8214             uint64_t data = MemARead (context, address + 4, 4, 0, &success);
   8215             if (!success)
   8216                 return false;
   8217 
   8218             CPSRWriteByInstr (data, 15, true);
   8219 
   8220             // BranchWritePC(MemA[address,4]);
   8221             uint64_t data2 = MemARead (context, address, 4, 0, &success);
   8222             if (!success)
   8223                 return false;
   8224 
   8225             BranchWritePC (context, data2);
   8226 
   8227             // if wback then R[n] = if increment then R[n]+8 else R[n]-8;
   8228             if (wback)
   8229             {
   8230                 context.type = eContextAdjustBaseRegister;
   8231                 if (increment)
   8232                 {
   8233                     context.SetOffset (8);
   8234                     if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, Rn + 8))
   8235                         return false;
   8236                 }
   8237                 else
   8238                 {
   8239                     context.SetOffset (-8);
   8240                     if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, Rn - 8))
   8241                         return false;
   8242                 }
   8243             } // if wback
   8244         }
   8245     } // if ConditionPassed()
   8246     return true;
   8247 }
   8248 
   8249 // Bitwise Exclusive OR (immediate) performs a bitwise exclusive OR of a register value and an immediate value,
   8250 // and writes the result to the destination register.  It can optionally update the condition flags based on
   8251 // the result.
   8252 bool
   8253 EmulateInstructionARM::EmulateEORImm (const uint32_t opcode, const ARMEncoding encoding)
   8254 {
   8255 #if 0
   8256     // ARM pseudo code...
   8257     if ConditionPassed() then
   8258         EncodingSpecificOperations();
   8259         result = R[n] EOR imm32;
   8260         if d == 15 then         // Can only occur for ARM encoding
   8261             ALUWritePC(result); // setflags is always FALSE here
   8262         else
   8263             R[d] = result;
   8264             if setflags then
   8265                 APSR.N = result<31>;
   8266                 APSR.Z = IsZeroBit(result);
   8267                 APSR.C = carry;
   8268                 // APSR.V unchanged
   8269 #endif
   8270 
   8271     bool success = false;
   8272 
   8273     if (ConditionPassed(opcode))
   8274     {
   8275         uint32_t Rd, Rn;
   8276         uint32_t imm32; // the immediate value to be ORed to the value obtained from Rn
   8277         bool setflags;
   8278         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   8279         switch (encoding)
   8280         {
   8281         case eEncodingT1:
   8282             Rd = Bits32(opcode, 11, 8);
   8283             Rn = Bits32(opcode, 19, 16);
   8284             setflags = BitIsSet(opcode, 20);
   8285             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   8286             // if Rd == '1111' && S == '1' then SEE TEQ (immediate);
   8287             if (Rd == 15 && setflags)
   8288                 return EmulateTEQImm (opcode, eEncodingT1);
   8289             if (Rd == 13 || (Rd == 15 && !setflags) || BadReg(Rn))
   8290                 return false;
   8291             break;
   8292         case eEncodingA1:
   8293             Rd = Bits32(opcode, 15, 12);
   8294             Rn = Bits32(opcode, 19, 16);
   8295             setflags = BitIsSet(opcode, 20);
   8296             imm32 = ARMExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   8297 
   8298             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8299             if (Rd == 15 && setflags)
   8300                 return EmulateSUBSPcLrEtc (opcode, encoding);
   8301             break;
   8302         default:
   8303             return false;
   8304         }
   8305 
   8306         // Read the first operand.
   8307         uint32_t val1 = ReadCoreReg(Rn, &success);
   8308         if (!success)
   8309             return false;
   8310 
   8311         uint32_t result = val1 ^ imm32;
   8312 
   8313         EmulateInstruction::Context context;
   8314         context.type = EmulateInstruction::eContextImmediate;
   8315         context.SetNoArgs ();
   8316 
   8317         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   8318             return false;
   8319     }
   8320     return true;
   8321 }
   8322 
   8323 // Bitwise Exclusive OR (register) performs a bitwise exclusive OR of a register value and an
   8324 // optionally-shifted register value, and writes the result to the destination register.
   8325 // It can optionally update the condition flags based on the result.
   8326 bool
   8327 EmulateInstructionARM::EmulateEORReg (const uint32_t opcode, const ARMEncoding encoding)
   8328 {
   8329 #if 0
   8330     // ARM pseudo code...
   8331     if ConditionPassed() then
   8332         EncodingSpecificOperations();
   8333         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   8334         result = R[n] EOR shifted;
   8335         if d == 15 then         // Can only occur for ARM encoding
   8336             ALUWritePC(result); // setflags is always FALSE here
   8337         else
   8338             R[d] = result;
   8339             if setflags then
   8340                 APSR.N = result<31>;
   8341                 APSR.Z = IsZeroBit(result);
   8342                 APSR.C = carry;
   8343                 // APSR.V unchanged
   8344 #endif
   8345 
   8346     bool success = false;
   8347 
   8348     if (ConditionPassed(opcode))
   8349     {
   8350         uint32_t Rd, Rn, Rm;
   8351         ARM_ShifterType shift_t;
   8352         uint32_t shift_n; // the shift applied to the value read from Rm
   8353         bool setflags;
   8354         uint32_t carry;
   8355         switch (encoding)
   8356         {
   8357         case eEncodingT1:
   8358             Rd = Rn = Bits32(opcode, 2, 0);
   8359             Rm = Bits32(opcode, 5, 3);
   8360             setflags = !InITBlock();
   8361             shift_t = SRType_LSL;
   8362             shift_n = 0;
   8363             break;
   8364         case eEncodingT2:
   8365             Rd = Bits32(opcode, 11, 8);
   8366             Rn = Bits32(opcode, 19, 16);
   8367             Rm = Bits32(opcode, 3, 0);
   8368             setflags = BitIsSet(opcode, 20);
   8369             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   8370             // if Rd == '1111' && S == '1' then SEE TEQ (register);
   8371             if (Rd == 15 && setflags)
   8372                 return EmulateTEQReg (opcode, eEncodingT1);
   8373             if (Rd == 13 || (Rd == 15 && !setflags) || BadReg(Rn) || BadReg(Rm))
   8374                 return false;
   8375             break;
   8376         case eEncodingA1:
   8377             Rd = Bits32(opcode, 15, 12);
   8378             Rn = Bits32(opcode, 19, 16);
   8379             Rm = Bits32(opcode, 3, 0);
   8380             setflags = BitIsSet(opcode, 20);
   8381             shift_n = DecodeImmShiftARM(opcode, shift_t);
   8382 
   8383             // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8384             if (Rd == 15 && setflags)
   8385                 return EmulateSUBSPcLrEtc (opcode, encoding);
   8386             break;
   8387         default:
   8388             return false;
   8389         }
   8390 
   8391         // Read the first operand.
   8392         uint32_t val1 = ReadCoreReg(Rn, &success);
   8393         if (!success)
   8394             return false;
   8395 
   8396         // Read the second operand.
   8397         uint32_t val2 = ReadCoreReg(Rm, &success);
   8398         if (!success)
   8399             return false;
   8400 
   8401         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   8402         if (!success)
   8403             return false;
   8404         uint32_t result = val1 ^ shifted;
   8405 
   8406         EmulateInstruction::Context context;
   8407         context.type = EmulateInstruction::eContextImmediate;
   8408         context.SetNoArgs ();
   8409 
   8410         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   8411             return false;
   8412     }
   8413     return true;
   8414 }
   8415 
   8416 // Bitwise OR (immediate) performs a bitwise (inclusive) OR of a register value and an immediate value, and
   8417 // writes the result to the destination register.  It can optionally update the condition flags based
   8418 // on the result.
   8419 bool
   8420 EmulateInstructionARM::EmulateORRImm (const uint32_t opcode, const ARMEncoding encoding)
   8421 {
   8422 #if 0
   8423     // ARM pseudo code...
   8424     if ConditionPassed() then
   8425         EncodingSpecificOperations();
   8426         result = R[n] OR imm32;
   8427         if d == 15 then         // Can only occur for ARM encoding
   8428             ALUWritePC(result); // setflags is always FALSE here
   8429         else
   8430             R[d] = result;
   8431             if setflags then
   8432                 APSR.N = result<31>;
   8433                 APSR.Z = IsZeroBit(result);
   8434                 APSR.C = carry;
   8435                 // APSR.V unchanged
   8436 #endif
   8437 
   8438     bool success = false;
   8439 
   8440     if (ConditionPassed(opcode))
   8441     {
   8442         uint32_t Rd, Rn;
   8443         uint32_t imm32; // the immediate value to be ORed to the value obtained from Rn
   8444         bool setflags;
   8445         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   8446         switch (encoding)
   8447         {
   8448         case eEncodingT1:
   8449             Rd = Bits32(opcode, 11, 8);
   8450             Rn = Bits32(opcode, 19, 16);
   8451             setflags = BitIsSet(opcode, 20);
   8452             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   8453             // if Rn == '1111' then SEE MOV (immediate);
   8454             if (Rn == 15)
   8455                 return EmulateMOVRdImm (opcode, eEncodingT2);
   8456             if (BadReg(Rd) || Rn == 13)
   8457                 return false;
   8458             break;
   8459         case eEncodingA1:
   8460             Rd = Bits32(opcode, 15, 12);
   8461             Rn = Bits32(opcode, 19, 16);
   8462             setflags = BitIsSet(opcode, 20);
   8463             imm32 = ARMExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   8464 
   8465             if (Rd == 15 && setflags)
   8466                 return EmulateSUBSPcLrEtc (opcode, encoding);
   8467             break;
   8468         default:
   8469             return false;
   8470         }
   8471 
   8472         // Read the first operand.
   8473         uint32_t val1 = ReadCoreReg(Rn, &success);
   8474         if (!success)
   8475             return false;
   8476 
   8477         uint32_t result = val1 | imm32;
   8478 
   8479         EmulateInstruction::Context context;
   8480         context.type = EmulateInstruction::eContextImmediate;
   8481         context.SetNoArgs ();
   8482 
   8483         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   8484             return false;
   8485     }
   8486     return true;
   8487 }
   8488 
   8489 // Bitwise OR (register) performs a bitwise (inclusive) OR of a register value and an optionally-shifted register
   8490 // value, and writes the result to the destination register.  It can optionally update the condition flags based
   8491 // on the result.
   8492 bool
   8493 EmulateInstructionARM::EmulateORRReg (const uint32_t opcode, const ARMEncoding encoding)
   8494 {
   8495 #if 0
   8496     // ARM pseudo code...
   8497     if ConditionPassed() then
   8498         EncodingSpecificOperations();
   8499         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   8500         result = R[n] OR shifted;
   8501         if d == 15 then         // Can only occur for ARM encoding
   8502             ALUWritePC(result); // setflags is always FALSE here
   8503         else
   8504             R[d] = result;
   8505             if setflags then
   8506                 APSR.N = result<31>;
   8507                 APSR.Z = IsZeroBit(result);
   8508                 APSR.C = carry;
   8509                 // APSR.V unchanged
   8510 #endif
   8511 
   8512     bool success = false;
   8513 
   8514     if (ConditionPassed(opcode))
   8515     {
   8516         uint32_t Rd, Rn, Rm;
   8517         ARM_ShifterType shift_t;
   8518         uint32_t shift_n; // the shift applied to the value read from Rm
   8519         bool setflags;
   8520         uint32_t carry;
   8521         switch (encoding)
   8522         {
   8523         case eEncodingT1:
   8524             Rd = Rn = Bits32(opcode, 2, 0);
   8525             Rm = Bits32(opcode, 5, 3);
   8526             setflags = !InITBlock();
   8527             shift_t = SRType_LSL;
   8528             shift_n = 0;
   8529             break;
   8530         case eEncodingT2:
   8531             Rd = Bits32(opcode, 11, 8);
   8532             Rn = Bits32(opcode, 19, 16);
   8533             Rm = Bits32(opcode, 3, 0);
   8534             setflags = BitIsSet(opcode, 20);
   8535             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   8536             // if Rn == '1111' then SEE MOV (register);
   8537             if (Rn == 15)
   8538                 return EmulateMOVRdRm (opcode, eEncodingT3);
   8539             if (BadReg(Rd) || Rn == 13 || BadReg(Rm))
   8540                 return false;
   8541             break;
   8542         case eEncodingA1:
   8543             Rd = Bits32(opcode, 15, 12);
   8544             Rn = Bits32(opcode, 19, 16);
   8545             Rm = Bits32(opcode, 3, 0);
   8546             setflags = BitIsSet(opcode, 20);
   8547             shift_n = DecodeImmShiftARM(opcode, shift_t);
   8548 
   8549             if (Rd == 15 && setflags)
   8550                 return EmulateSUBSPcLrEtc (opcode, encoding);
   8551             break;
   8552         default:
   8553             return false;
   8554         }
   8555 
   8556         // Read the first operand.
   8557         uint32_t val1 = ReadCoreReg(Rn, &success);
   8558         if (!success)
   8559             return false;
   8560 
   8561         // Read the second operand.
   8562         uint32_t val2 = ReadCoreReg(Rm, &success);
   8563         if (!success)
   8564             return false;
   8565 
   8566         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   8567         if (!success)
   8568             return false;
   8569         uint32_t result = val1 | shifted;
   8570 
   8571         EmulateInstruction::Context context;
   8572         context.type = EmulateInstruction::eContextImmediate;
   8573         context.SetNoArgs ();
   8574 
   8575         if (!WriteCoreRegOptionalFlags(context, result, Rd, setflags, carry))
   8576             return false;
   8577     }
   8578     return true;
   8579 }
   8580 
   8581 // Reverse Subtract (immediate) subtracts a register value from an immediate value, and writes the result to
   8582 // the destination register. It can optionally update the condition flags based on the result.
   8583 bool
   8584 EmulateInstructionARM::EmulateRSBImm (const uint32_t opcode, const ARMEncoding encoding)
   8585 {
   8586 #if 0
   8587     // ARM pseudo code...
   8588     if ConditionPassed() then
   8589         EncodingSpecificOperations();
   8590         (result, carry, overflow) = AddWithCarry(NOT(R[n]), imm32, '1');
   8591         if d == 15 then         // Can only occur for ARM encoding
   8592             ALUWritePC(result); // setflags is always FALSE here
   8593         else
   8594             R[d] = result;
   8595             if setflags then
   8596                 APSR.N = result<31>;
   8597                 APSR.Z = IsZeroBit(result);
   8598                 APSR.C = carry;
   8599                 APSR.V = overflow;
   8600 #endif
   8601 
   8602     bool success = false;
   8603 
   8604     uint32_t Rd; // the destination register
   8605     uint32_t Rn; // the first operand
   8606     bool setflags;
   8607     uint32_t imm32; // the immediate value to be added to the value obtained from Rn
   8608     switch (encoding) {
   8609     case eEncodingT1:
   8610         Rd = Bits32(opcode, 2, 0);
   8611         Rn = Bits32(opcode, 5, 3);
   8612         setflags = !InITBlock();
   8613         imm32 = 0;
   8614         break;
   8615     case eEncodingT2:
   8616         Rd = Bits32(opcode, 11, 8);
   8617         Rn = Bits32(opcode, 19, 16);
   8618         setflags = BitIsSet(opcode, 20);
   8619         imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   8620         if (BadReg(Rd) || BadReg(Rn))
   8621             return false;
   8622         break;
   8623     case eEncodingA1:
   8624         Rd = Bits32(opcode, 15, 12);
   8625         Rn = Bits32(opcode, 19, 16);
   8626         setflags = BitIsSet(opcode, 20);
   8627         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   8628 
   8629         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8630         if (Rd == 15 && setflags)
   8631             return EmulateSUBSPcLrEtc (opcode, encoding);
   8632         break;
   8633     default:
   8634         return false;
   8635     }
   8636     // Read the register value from the operand register Rn.
   8637     uint32_t reg_val = ReadCoreReg(Rn, &success);
   8638     if (!success)
   8639         return false;
   8640 
   8641     AddWithCarryResult res = AddWithCarry(~reg_val, imm32, 1);
   8642 
   8643     EmulateInstruction::Context context;
   8644     context.type = EmulateInstruction::eContextImmediate;
   8645     context.SetNoArgs ();
   8646 
   8647     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   8648         return false;
   8649 
   8650     return true;
   8651 }
   8652 
   8653 // Reverse Subtract (register) subtracts a register value from an optionally-shifted register value, and writes the
   8654 // result to the destination register. It can optionally update the condition flags based on the result.
   8655 bool
   8656 EmulateInstructionARM::EmulateRSBReg (const uint32_t opcode, const ARMEncoding encoding)
   8657 {
   8658 #if 0
   8659     // ARM pseudo code...
   8660     if ConditionPassed() then
   8661         EncodingSpecificOperations();
   8662         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   8663         (result, carry, overflow) = AddWithCarry(NOT(R[n]), shifted, '1');
   8664         if d == 15 then         // Can only occur for ARM encoding
   8665             ALUWritePC(result); // setflags is always FALSE here
   8666         else
   8667             R[d] = result;
   8668             if setflags then
   8669                 APSR.N = result<31>;
   8670                 APSR.Z = IsZeroBit(result);
   8671                 APSR.C = carry;
   8672                 APSR.V = overflow;
   8673 #endif
   8674 
   8675     bool success = false;
   8676 
   8677     uint32_t Rd; // the destination register
   8678     uint32_t Rn; // the first operand
   8679     uint32_t Rm; // the second operand
   8680     bool setflags;
   8681     ARM_ShifterType shift_t;
   8682     uint32_t shift_n; // the shift applied to the value read from Rm
   8683     switch (encoding) {
   8684     case eEncodingT1:
   8685         Rd = Bits32(opcode, 11, 8);
   8686         Rn = Bits32(opcode, 19, 16);
   8687         Rm = Bits32(opcode, 3, 0);
   8688         setflags = BitIsSet(opcode, 20);
   8689         shift_n = DecodeImmShiftThumb(opcode, shift_t);
   8690         // if (BadReg(d) || BadReg(m)) then UNPREDICTABLE;
   8691         if (BadReg(Rd) || BadReg(Rn) || BadReg(Rm))
   8692             return false;
   8693         break;
   8694     case eEncodingA1:
   8695         Rd = Bits32(opcode, 15, 12);
   8696         Rn = Bits32(opcode, 19, 16);
   8697         Rm = Bits32(opcode, 3, 0);
   8698         setflags = BitIsSet(opcode, 20);
   8699         shift_n = DecodeImmShiftARM(opcode, shift_t);
   8700 
   8701         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8702         if (Rd == 15 && setflags)
   8703             return EmulateSUBSPcLrEtc (opcode, encoding);
   8704         break;
   8705     default:
   8706         return false;
   8707     }
   8708     // Read the register value from register Rn.
   8709     uint32_t val1 = ReadCoreReg(Rn, &success);
   8710     if (!success)
   8711         return false;
   8712 
   8713     // Read the register value from register Rm.
   8714     uint32_t val2 = ReadCoreReg(Rm, &success);
   8715     if (!success)
   8716         return false;
   8717 
   8718     uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   8719     if (!success)
   8720         return false;
   8721     AddWithCarryResult res = AddWithCarry(~val1, shifted, 1);
   8722 
   8723     EmulateInstruction::Context context;
   8724     context.type = EmulateInstruction::eContextImmediate;
   8725     context.SetNoArgs();
   8726     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   8727         return false;
   8728 
   8729     return true;
   8730 }
   8731 
   8732 // Reverse Subtract with Carry (immediate) subtracts a register value and the value of NOT (Carry flag) from
   8733 // an immediate value, and writes the result to the destination register. It can optionally update the condition
   8734 // flags based on the result.
   8735 bool
   8736 EmulateInstructionARM::EmulateRSCImm (const uint32_t opcode, const ARMEncoding encoding)
   8737 {
   8738 #if 0
   8739     // ARM pseudo code...
   8740     if ConditionPassed() then
   8741         EncodingSpecificOperations();
   8742         (result, carry, overflow) = AddWithCarry(NOT(R[n]), imm32, APSR.C);
   8743         if d == 15 then
   8744             ALUWritePC(result); // setflags is always FALSE here
   8745         else
   8746             R[d] = result;
   8747             if setflags then
   8748                 APSR.N = result<31>;
   8749                 APSR.Z = IsZeroBit(result);
   8750                 APSR.C = carry;
   8751                 APSR.V = overflow;
   8752 #endif
   8753 
   8754     bool success = false;
   8755 
   8756     uint32_t Rd; // the destination register
   8757     uint32_t Rn; // the first operand
   8758     bool setflags;
   8759     uint32_t imm32; // the immediate value to be added to the value obtained from Rn
   8760     switch (encoding) {
   8761     case eEncodingA1:
   8762         Rd = Bits32(opcode, 15, 12);
   8763         Rn = Bits32(opcode, 19, 16);
   8764         setflags = BitIsSet(opcode, 20);
   8765         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   8766 
   8767         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8768         if (Rd == 15 && setflags)
   8769             return EmulateSUBSPcLrEtc  (opcode, encoding);
   8770         break;
   8771     default:
   8772         return false;
   8773     }
   8774     // Read the register value from the operand register Rn.
   8775     uint32_t reg_val = ReadCoreReg(Rn, &success);
   8776     if (!success)
   8777         return false;
   8778 
   8779     AddWithCarryResult res = AddWithCarry(~reg_val, imm32, APSR_C);
   8780 
   8781     EmulateInstruction::Context context;
   8782     context.type = EmulateInstruction::eContextImmediate;
   8783     context.SetNoArgs ();
   8784 
   8785     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   8786         return false;
   8787 
   8788     return true;
   8789 }
   8790 
   8791 // Reverse Subtract with Carry (register) subtracts a register value and the value of NOT (Carry flag) from an
   8792 // optionally-shifted register value, and writes the result to the destination register. It can optionally update the
   8793 // condition flags based on the result.
   8794 bool
   8795 EmulateInstructionARM::EmulateRSCReg (const uint32_t opcode, const ARMEncoding encoding)
   8796 {
   8797 #if 0
   8798     // ARM pseudo code...
   8799     if ConditionPassed() then
   8800         EncodingSpecificOperations();
   8801         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   8802         (result, carry, overflow) = AddWithCarry(NOT(R[n]), shifted, APSR.C);
   8803         if d == 15 then
   8804             ALUWritePC(result); // setflags is always FALSE here
   8805         else
   8806             R[d] = result;
   8807             if setflags then
   8808                 APSR.N = result<31>;
   8809                 APSR.Z = IsZeroBit(result);
   8810                 APSR.C = carry;
   8811                 APSR.V = overflow;
   8812 #endif
   8813 
   8814     bool success = false;
   8815 
   8816     uint32_t Rd; // the destination register
   8817     uint32_t Rn; // the first operand
   8818     uint32_t Rm; // the second operand
   8819     bool setflags;
   8820     ARM_ShifterType shift_t;
   8821     uint32_t shift_n; // the shift applied to the value read from Rm
   8822     switch (encoding) {
   8823     case eEncodingA1:
   8824         Rd = Bits32(opcode, 15, 12);
   8825         Rn = Bits32(opcode, 19, 16);
   8826         Rm = Bits32(opcode, 3, 0);
   8827         setflags = BitIsSet(opcode, 20);
   8828         shift_n = DecodeImmShiftARM(opcode, shift_t);
   8829 
   8830         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8831         if (Rd == 15 && setflags)
   8832             return EmulateSUBSPcLrEtc (opcode, encoding);
   8833         break;
   8834     default:
   8835         return false;
   8836     }
   8837     // Read the register value from register Rn.
   8838     uint32_t val1 = ReadCoreReg(Rn, &success);
   8839     if (!success)
   8840         return false;
   8841 
   8842     // Read the register value from register Rm.
   8843     uint32_t val2 = ReadCoreReg(Rm, &success);
   8844     if (!success)
   8845         return false;
   8846 
   8847     uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   8848     if (!success)
   8849         return false;
   8850     AddWithCarryResult res = AddWithCarry(~val1, shifted, APSR_C);
   8851 
   8852     EmulateInstruction::Context context;
   8853     context.type = EmulateInstruction::eContextImmediate;
   8854     context.SetNoArgs();
   8855     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   8856         return false;
   8857 
   8858     return true;
   8859 }
   8860 
   8861 // Subtract with Carry (immediate) subtracts an immediate value and the value of
   8862 // NOT (Carry flag) from a register value, and writes the result to the destination register.
   8863 // It can optionally update the condition flags based on the result.
   8864 bool
   8865 EmulateInstructionARM::EmulateSBCImm (const uint32_t opcode, const ARMEncoding encoding)
   8866 {
   8867 #if 0
   8868     // ARM pseudo code...
   8869     if ConditionPassed() then
   8870         EncodingSpecificOperations();
   8871         (result, carry, overflow) = AddWithCarry(R[n], NOT(imm32), APSR.C);
   8872         if d == 15 then         // Can only occur for ARM encoding
   8873             ALUWritePC(result); // setflags is always FALSE here
   8874         else
   8875             R[d] = result;
   8876             if setflags then
   8877                 APSR.N = result<31>;
   8878                 APSR.Z = IsZeroBit(result);
   8879                 APSR.C = carry;
   8880                 APSR.V = overflow;
   8881 #endif
   8882 
   8883     bool success = false;
   8884 
   8885     uint32_t Rd; // the destination register
   8886     uint32_t Rn; // the first operand
   8887     bool setflags;
   8888     uint32_t imm32; // the immediate value to be added to the value obtained from Rn
   8889     switch (encoding) {
   8890     case eEncodingT1:
   8891         Rd = Bits32(opcode, 11, 8);
   8892         Rn = Bits32(opcode, 19, 16);
   8893         setflags = BitIsSet(opcode, 20);
   8894         imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   8895         if (BadReg(Rd) || BadReg(Rn))
   8896             return false;
   8897         break;
   8898     case eEncodingA1:
   8899         Rd = Bits32(opcode, 15, 12);
   8900         Rn = Bits32(opcode, 19, 16);
   8901         setflags = BitIsSet(opcode, 20);
   8902         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   8903 
   8904         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8905         if (Rd == 15 && setflags)
   8906             return EmulateSUBSPcLrEtc (opcode, encoding);
   8907         break;
   8908     default:
   8909         return false;
   8910     }
   8911     // Read the register value from the operand register Rn.
   8912     uint32_t reg_val = ReadCoreReg(Rn, &success);
   8913     if (!success)
   8914         return false;
   8915 
   8916     AddWithCarryResult res = AddWithCarry(reg_val, ~imm32, APSR_C);
   8917 
   8918     EmulateInstruction::Context context;
   8919     context.type = EmulateInstruction::eContextImmediate;
   8920     context.SetNoArgs ();
   8921 
   8922     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   8923         return false;
   8924 
   8925     return true;
   8926 }
   8927 
   8928 // Subtract with Carry (register) subtracts an optionally-shifted register value and the value of
   8929 // NOT (Carry flag) from a register value, and writes the result to the destination register.
   8930 // It can optionally update the condition flags based on the result.
   8931 bool
   8932 EmulateInstructionARM::EmulateSBCReg (const uint32_t opcode, const ARMEncoding encoding)
   8933 {
   8934 #if 0
   8935     // ARM pseudo code...
   8936     if ConditionPassed() then
   8937         EncodingSpecificOperations();
   8938         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   8939         (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), APSR.C);
   8940         if d == 15 then         // Can only occur for ARM encoding
   8941             ALUWritePC(result); // setflags is always FALSE here
   8942         else
   8943             R[d] = result;
   8944             if setflags then
   8945                 APSR.N = result<31>;
   8946                 APSR.Z = IsZeroBit(result);
   8947                 APSR.C = carry;
   8948                 APSR.V = overflow;
   8949 #endif
   8950 
   8951     bool success = false;
   8952 
   8953     uint32_t Rd; // the destination register
   8954     uint32_t Rn; // the first operand
   8955     uint32_t Rm; // the second operand
   8956     bool setflags;
   8957     ARM_ShifterType shift_t;
   8958     uint32_t shift_n; // the shift applied to the value read from Rm
   8959     switch (encoding) {
   8960     case eEncodingT1:
   8961         Rd = Rn = Bits32(opcode, 2, 0);
   8962         Rm = Bits32(opcode, 5, 3);
   8963         setflags = !InITBlock();
   8964         shift_t = SRType_LSL;
   8965         shift_n = 0;
   8966         break;
   8967     case eEncodingT2:
   8968         Rd = Bits32(opcode, 11, 8);
   8969         Rn = Bits32(opcode, 19, 16);
   8970         Rm = Bits32(opcode, 3, 0);
   8971         setflags = BitIsSet(opcode, 20);
   8972         shift_n = DecodeImmShiftThumb(opcode, shift_t);
   8973         if (BadReg(Rd) || BadReg(Rn) || BadReg(Rm))
   8974             return false;
   8975         break;
   8976     case eEncodingA1:
   8977         Rd = Bits32(opcode, 15, 12);
   8978         Rn = Bits32(opcode, 19, 16);
   8979         Rm = Bits32(opcode, 3, 0);
   8980         setflags = BitIsSet(opcode, 20);
   8981         shift_n = DecodeImmShiftARM(opcode, shift_t);
   8982 
   8983         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   8984         if (Rd == 15 && setflags)
   8985             return EmulateSUBSPcLrEtc (opcode, encoding);
   8986         break;
   8987     default:
   8988         return false;
   8989     }
   8990     // Read the register value from register Rn.
   8991     uint32_t val1 = ReadCoreReg(Rn, &success);
   8992     if (!success)
   8993         return false;
   8994 
   8995     // Read the register value from register Rm.
   8996     uint32_t val2 = ReadCoreReg(Rm, &success);
   8997     if (!success)
   8998         return false;
   8999 
   9000     uint32_t shifted = Shift(val2, shift_t, shift_n, APSR_C, &success);
   9001     if (!success)
   9002         return false;
   9003     AddWithCarryResult res = AddWithCarry(val1, ~shifted, APSR_C);
   9004 
   9005     EmulateInstruction::Context context;
   9006     context.type = EmulateInstruction::eContextImmediate;
   9007     context.SetNoArgs();
   9008     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   9009         return false;
   9010 
   9011     return true;
   9012 }
   9013 
   9014 // This instruction subtracts an immediate value from a register value, and writes the result
   9015 // to the destination register.  It can optionally update the condition flags based on the result.
   9016 bool
   9017 EmulateInstructionARM::EmulateSUBImmThumb (const uint32_t opcode, const ARMEncoding encoding)
   9018 {
   9019 #if 0
   9020     // ARM pseudo code...
   9021     if ConditionPassed() then
   9022         EncodingSpecificOperations();
   9023         (result, carry, overflow) = AddWithCarry(R[n], NOT(imm32), '1');
   9024         R[d] = result;
   9025         if setflags then
   9026             APSR.N = result<31>;
   9027             APSR.Z = IsZeroBit(result);
   9028             APSR.C = carry;
   9029             APSR.V = overflow;
   9030 #endif
   9031 
   9032     bool success = false;
   9033 
   9034     uint32_t Rd; // the destination register
   9035     uint32_t Rn; // the first operand
   9036     bool setflags;
   9037     uint32_t imm32; // the immediate value to be subtracted from the value obtained from Rn
   9038     switch (encoding) {
   9039     case eEncodingT1:
   9040         Rd = Bits32(opcode, 2, 0);
   9041         Rn = Bits32(opcode, 5, 3);
   9042         setflags = !InITBlock();
   9043         imm32 = Bits32(opcode, 8, 6); // imm32 = ZeroExtend(imm3, 32)
   9044         break;
   9045     case eEncodingT2:
   9046         Rd = Rn = Bits32(opcode, 10, 8);
   9047         setflags = !InITBlock();
   9048         imm32 = Bits32(opcode, 7, 0); // imm32 = ZeroExtend(imm8, 32)
   9049         break;
   9050     case eEncodingT3:
   9051         Rd = Bits32(opcode, 11, 8);
   9052         Rn = Bits32(opcode, 19, 16);
   9053         setflags = BitIsSet(opcode, 20);
   9054         imm32 = ThumbExpandImm(opcode); // imm32 = ThumbExpandImm(i:imm3:imm8)
   9055 
   9056         // if Rd == '1111' && S == '1' then SEE CMP (immediate);
   9057         if (Rd == 15 && setflags)
   9058             return EmulateCMPImm (opcode, eEncodingT2);
   9059 
   9060         // if Rn == '1101' then SEE SUB (SP minus immediate);
   9061         if (Rn == 13)
   9062             return EmulateSUBSPImm (opcode, eEncodingT2);
   9063 
   9064         // if d == 13 || (d == 15 && S == '0') || n == 15 then UNPREDICTABLE;
   9065         if (Rd == 13 || (Rd == 15 && !setflags) || Rn == 15)
   9066             return false;
   9067         break;
   9068     case eEncodingT4:
   9069         Rd = Bits32(opcode, 11, 8);
   9070         Rn = Bits32(opcode, 19, 16);
   9071         setflags = BitIsSet(opcode, 20);
   9072         imm32 = ThumbImm12(opcode); // imm32 = ZeroExtend(i:imm3:imm8, 32)
   9073 
   9074         // if Rn == '1111' then SEE ADR;
   9075         if (Rn == 15)
   9076             return EmulateADR (opcode, eEncodingT2);
   9077 
   9078         // if Rn == '1101' then SEE SUB (SP minus immediate);
   9079         if (Rn == 13)
   9080             return EmulateSUBSPImm (opcode, eEncodingT3);
   9081 
   9082         if (BadReg(Rd))
   9083             return false;
   9084         break;
   9085     default:
   9086         return false;
   9087     }
   9088     // Read the register value from the operand register Rn.
   9089     uint32_t reg_val = ReadCoreReg(Rn, &success);
   9090     if (!success)
   9091         return false;
   9092 
   9093     AddWithCarryResult res = AddWithCarry(reg_val, ~imm32, 1);
   9094 
   9095     EmulateInstruction::Context context;
   9096     context.type = EmulateInstruction::eContextImmediate;
   9097     context.SetNoArgs ();
   9098 
   9099     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   9100         return false;
   9101 
   9102     return true;
   9103 }
   9104 
   9105 // This instruction subtracts an immediate value from a register value, and writes the result
   9106 // to the destination register.  It can optionally update the condition flags based on the result.
   9107 bool
   9108 EmulateInstructionARM::EmulateSUBImmARM (const uint32_t opcode, const ARMEncoding encoding)
   9109 {
   9110 #if 0
   9111     // ARM pseudo code...
   9112     if ConditionPassed() then
   9113         EncodingSpecificOperations();
   9114         (result, carry, overflow) = AddWithCarry(R[n], NOT(imm32), '1');
   9115         if d == 15 then
   9116             ALUWritePC(result); // setflags is always FALSE here
   9117         else
   9118             R[d] = result;
   9119             if setflags then
   9120                 APSR.N = result<31>;
   9121                 APSR.Z = IsZeroBit(result);
   9122                 APSR.C = carry;
   9123                 APSR.V = overflow;
   9124 #endif
   9125 
   9126     bool success = false;
   9127 
   9128     uint32_t Rd; // the destination register
   9129     uint32_t Rn; // the first operand
   9130     bool setflags;
   9131     uint32_t imm32; // the immediate value to be subtracted from the value obtained from Rn
   9132     switch (encoding) {
   9133     case eEncodingA1:
   9134         Rd = Bits32(opcode, 15, 12);
   9135         Rn = Bits32(opcode, 19, 16);
   9136         setflags = BitIsSet(opcode, 20);
   9137         imm32 = ARMExpandImm(opcode); // imm32 = ARMExpandImm(imm12)
   9138 
   9139         // if Rn == '1111' && S == '0' then SEE ADR;
   9140         if (Rn == 15 && !setflags)
   9141             return EmulateADR (opcode, eEncodingA2);
   9142 
   9143         // if Rn == '1101' then SEE SUB (SP minus immediate);
   9144         if (Rn == 13)
   9145             return EmulateSUBSPImm (opcode, eEncodingA1);
   9146 
   9147         // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions;
   9148         if (Rd == 15 && setflags)
   9149             return EmulateSUBSPcLrEtc (opcode, encoding);
   9150         break;
   9151     default:
   9152         return false;
   9153     }
   9154     // Read the register value from the operand register Rn.
   9155     uint32_t reg_val = ReadCoreReg(Rn, &success);
   9156     if (!success)
   9157         return false;
   9158 
   9159     AddWithCarryResult res = AddWithCarry(reg_val, ~imm32, 1);
   9160 
   9161     EmulateInstruction::Context context;
   9162     context.type = EmulateInstruction::eContextImmediate;
   9163     context.SetNoArgs ();
   9164 
   9165     if (!WriteCoreRegOptionalFlags(context, res.result, Rd, setflags, res.carry_out, res.overflow))
   9166         return false;
   9167 
   9168     return true;
   9169 }
   9170 
   9171 // Test Equivalence (immediate) performs a bitwise exclusive OR operation on a register value and an
   9172 // immediate value.  It updates the condition flags based on the result, and discards the result.
   9173 bool
   9174 EmulateInstructionARM::EmulateTEQImm (const uint32_t opcode, const ARMEncoding encoding)
   9175 {
   9176 #if 0
   9177     // ARM pseudo code...
   9178     if ConditionPassed() then
   9179         EncodingSpecificOperations();
   9180         result = R[n] EOR imm32;
   9181         APSR.N = result<31>;
   9182         APSR.Z = IsZeroBit(result);
   9183         APSR.C = carry;
   9184         // APSR.V unchanged
   9185 #endif
   9186 
   9187     bool success = false;
   9188 
   9189     if (ConditionPassed(opcode))
   9190     {
   9191         uint32_t Rn;
   9192         uint32_t imm32; // the immediate value to be ANDed to the value obtained from Rn
   9193         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   9194         switch (encoding)
   9195         {
   9196         case eEncodingT1:
   9197             Rn = Bits32(opcode, 19, 16);
   9198             imm32 = ThumbExpandImm_C (opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   9199             if (BadReg(Rn))
   9200                 return false;
   9201             break;
   9202         case eEncodingA1:
   9203             Rn = Bits32(opcode, 19, 16);
   9204             imm32 = ARMExpandImm_C (opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   9205             break;
   9206         default:
   9207             return false;
   9208         }
   9209 
   9210         // Read the first operand.
   9211         uint32_t val1 = ReadCoreReg(Rn, &success);
   9212         if (!success)
   9213             return false;
   9214 
   9215         uint32_t result = val1 ^ imm32;
   9216 
   9217         EmulateInstruction::Context context;
   9218         context.type = EmulateInstruction::eContextImmediate;
   9219         context.SetNoArgs ();
   9220 
   9221         if (!WriteFlags(context, result, carry))
   9222             return false;
   9223     }
   9224     return true;
   9225 }
   9226 
   9227 // Test Equivalence (register) performs a bitwise exclusive OR operation on a register value and an
   9228 // optionally-shifted register value.  It updates the condition flags based on the result, and discards
   9229 // the result.
   9230 bool
   9231 EmulateInstructionARM::EmulateTEQReg (const uint32_t opcode, const ARMEncoding encoding)
   9232 {
   9233 #if 0
   9234     // ARM pseudo code...
   9235     if ConditionPassed() then
   9236         EncodingSpecificOperations();
   9237         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   9238         result = R[n] EOR shifted;
   9239         APSR.N = result<31>;
   9240         APSR.Z = IsZeroBit(result);
   9241         APSR.C = carry;
   9242         // APSR.V unchanged
   9243 #endif
   9244 
   9245     bool success = false;
   9246 
   9247     if (ConditionPassed(opcode))
   9248     {
   9249         uint32_t Rn, Rm;
   9250         ARM_ShifterType shift_t;
   9251         uint32_t shift_n; // the shift applied to the value read from Rm
   9252         uint32_t carry;
   9253         switch (encoding)
   9254         {
   9255         case eEncodingT1:
   9256             Rn = Bits32(opcode, 19, 16);
   9257             Rm = Bits32(opcode, 3, 0);
   9258             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   9259             if (BadReg(Rn) || BadReg(Rm))
   9260                 return false;
   9261             break;
   9262         case eEncodingA1:
   9263             Rn = Bits32(opcode, 19, 16);
   9264             Rm = Bits32(opcode, 3, 0);
   9265             shift_n = DecodeImmShiftARM(opcode, shift_t);
   9266             break;
   9267         default:
   9268             return false;
   9269         }
   9270 
   9271         // Read the first operand.
   9272         uint32_t val1 = ReadCoreReg(Rn, &success);
   9273         if (!success)
   9274             return false;
   9275 
   9276         // Read the second operand.
   9277         uint32_t val2 = ReadCoreReg(Rm, &success);
   9278         if (!success)
   9279             return false;
   9280 
   9281         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   9282         if (!success)
   9283             return false;
   9284         uint32_t result = val1 ^ shifted;
   9285 
   9286         EmulateInstruction::Context context;
   9287         context.type = EmulateInstruction::eContextImmediate;
   9288         context.SetNoArgs ();
   9289 
   9290         if (!WriteFlags(context, result, carry))
   9291             return false;
   9292     }
   9293     return true;
   9294 }
   9295 
   9296 // Test (immediate) performs a bitwise AND operation on a register value and an immediate value.
   9297 // It updates the condition flags based on the result, and discards the result.
   9298 bool
   9299 EmulateInstructionARM::EmulateTSTImm (const uint32_t opcode, const ARMEncoding encoding)
   9300 {
   9301 #if 0
   9302     // ARM pseudo code...
   9303     if ConditionPassed() then
   9304         EncodingSpecificOperations();
   9305         result = R[n] AND imm32;
   9306         APSR.N = result<31>;
   9307         APSR.Z = IsZeroBit(result);
   9308         APSR.C = carry;
   9309         // APSR.V unchanged
   9310 #endif
   9311 
   9312     bool success = false;
   9313 
   9314     if (ConditionPassed(opcode))
   9315     {
   9316         uint32_t Rn;
   9317         uint32_t imm32; // the immediate value to be ANDed to the value obtained from Rn
   9318         uint32_t carry; // the carry bit after ARM/Thumb Expand operation
   9319         switch (encoding)
   9320         {
   9321         case eEncodingT1:
   9322             Rn = Bits32(opcode, 19, 16);
   9323             imm32 = ThumbExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ThumbExpandImm(i:imm3:imm8, APSR.C)
   9324             if (BadReg(Rn))
   9325                 return false;
   9326             break;
   9327         case eEncodingA1:
   9328             Rn = Bits32(opcode, 19, 16);
   9329             imm32 = ARMExpandImm_C(opcode, APSR_C, carry); // (imm32, carry) = ARMExpandImm(imm12, APSR.C)
   9330             break;
   9331         default:
   9332             return false;
   9333         }
   9334 
   9335         // Read the first operand.
   9336         uint32_t val1 = ReadCoreReg(Rn, &success);
   9337         if (!success)
   9338             return false;
   9339 
   9340         uint32_t result = val1 & imm32;
   9341 
   9342         EmulateInstruction::Context context;
   9343         context.type = EmulateInstruction::eContextImmediate;
   9344         context.SetNoArgs ();
   9345 
   9346         if (!WriteFlags(context, result, carry))
   9347             return false;
   9348     }
   9349     return true;
   9350 }
   9351 
   9352 // Test (register) performs a bitwise AND operation on a register value and an optionally-shifted register value.
   9353 // It updates the condition flags based on the result, and discards the result.
   9354 bool
   9355 EmulateInstructionARM::EmulateTSTReg (const uint32_t opcode, const ARMEncoding encoding)
   9356 {
   9357 #if 0
   9358     // ARM pseudo code...
   9359     if ConditionPassed() then
   9360         EncodingSpecificOperations();
   9361         (shifted, carry) = Shift_C(R[m], shift_t, shift_n, APSR.C);
   9362         result = R[n] AND shifted;
   9363         APSR.N = result<31>;
   9364         APSR.Z = IsZeroBit(result);
   9365         APSR.C = carry;
   9366         // APSR.V unchanged
   9367 #endif
   9368 
   9369     bool success = false;
   9370 
   9371     if (ConditionPassed(opcode))
   9372     {
   9373         uint32_t Rn, Rm;
   9374         ARM_ShifterType shift_t;
   9375         uint32_t shift_n; // the shift applied to the value read from Rm
   9376         uint32_t carry;
   9377         switch (encoding)
   9378         {
   9379         case eEncodingT1:
   9380             Rn = Bits32(opcode, 2, 0);
   9381             Rm = Bits32(opcode, 5, 3);
   9382             shift_t = SRType_LSL;
   9383             shift_n = 0;
   9384             break;
   9385         case eEncodingT2:
   9386             Rn = Bits32(opcode, 19, 16);
   9387             Rm = Bits32(opcode, 3, 0);
   9388             shift_n = DecodeImmShiftThumb(opcode, shift_t);
   9389             if (BadReg(Rn) || BadReg(Rm))
   9390                 return false;
   9391             break;
   9392         case eEncodingA1:
   9393             Rn = Bits32(opcode, 19, 16);
   9394             Rm = Bits32(opcode, 3, 0);
   9395             shift_n = DecodeImmShiftARM(opcode, shift_t);
   9396             break;
   9397         default:
   9398             return false;
   9399         }
   9400 
   9401         // Read the first operand.
   9402         uint32_t val1 = ReadCoreReg(Rn, &success);
   9403         if (!success)
   9404             return false;
   9405 
   9406         // Read the second operand.
   9407         uint32_t val2 = ReadCoreReg(Rm, &success);
   9408         if (!success)
   9409             return false;
   9410 
   9411         uint32_t shifted = Shift_C(val2, shift_t, shift_n, APSR_C, carry, &success);
   9412         if (!success)
   9413             return false;
   9414         uint32_t result = val1 & shifted;
   9415 
   9416         EmulateInstruction::Context context;
   9417         context.type = EmulateInstruction::eContextImmediate;
   9418         context.SetNoArgs ();
   9419 
   9420         if (!WriteFlags(context, result, carry))
   9421             return false;
   9422     }
   9423     return true;
   9424 }
   9425 
   9426 // A8.6.216 SUB (SP minus register)
   9427 bool
   9428 EmulateInstructionARM::EmulateSUBSPReg (const uint32_t opcode, const ARMEncoding encoding)
   9429 {
   9430 #if 0
   9431     if ConditionPassed() then
   9432         EncodingSpecificOperations();
   9433         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9434         (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), 1);
   9435         if d == 15 then // Can only occur for ARM encoding
   9436             ALUWritePC(result); // setflags is always FALSE here
   9437         else
   9438             R[d] = result;
   9439             if setflags then
   9440                 APSR.N = result<31>;
   9441                 APSR.Z = IsZeroBit(result);
   9442                 APSR.C = carry;
   9443                 APSR.V = overflow;
   9444 #endif
   9445 
   9446     bool success = false;
   9447 
   9448     if (ConditionPassed(opcode))
   9449     {
   9450         uint32_t d;
   9451         uint32_t m;
   9452         bool setflags;
   9453         ARM_ShifterType shift_t;
   9454         uint32_t shift_n;
   9455 
   9456         switch (encoding)
   9457         {
   9458             case eEncodingT1:
   9459                 // d = UInt(Rd); m = UInt(Rm); setflags = (S == 1);
   9460                 d = Bits32 (opcode, 11, 8);
   9461                 m = Bits32 (opcode, 3, 0);
   9462                 setflags = BitIsSet (opcode, 20);
   9463 
   9464                 // (shift_t, shift_n) = DecodeImmShift(type, imm3:imm2);
   9465                 shift_n = DecodeImmShiftThumb (opcode, shift_t);
   9466 
   9467                 // if d == 13 && (shift_t != SRType_LSL || shift_n > 3) then UNPREDICTABLE;
   9468                 if ((d == 13) && ((shift_t != SRType_LSL) || (shift_n > 3)))
   9469                     return false;
   9470 
   9471                 // if d == 15 || BadReg(m) then UNPREDICTABLE;
   9472                 if ((d == 15) || BadReg (m))
   9473                     return false;
   9474                 break;
   9475 
   9476             case eEncodingA1:
   9477                 // d = UInt(Rd); m = UInt(Rm); setflags = (S == 1);
   9478                 d = Bits32 (opcode, 15, 12);
   9479                 m = Bits32 (opcode, 3, 0);
   9480                 setflags = BitIsSet (opcode, 20);
   9481 
   9482                 // if Rd == 1111 && S == 1 then SEE SUBS PC, LR and related instructions;
   9483                 if (d == 15 && setflags)
   9484                     EmulateSUBSPcLrEtc (opcode, encoding);
   9485 
   9486                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   9487                 shift_n = DecodeImmShiftARM (opcode, shift_t);
   9488                 break;
   9489 
   9490             default:
   9491                 return false;
   9492         }
   9493 
   9494         // shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9495         uint32_t Rm = ReadCoreReg (m, &success);
   9496         if (!success)
   9497             return false;
   9498 
   9499         uint32_t shifted = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   9500         if (!success)
   9501             return false;
   9502 
   9503         // (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), 1);
   9504         uint32_t sp_val = ReadCoreReg (SP_REG, &success);
   9505         if (!success)
   9506             return false;
   9507 
   9508         AddWithCarryResult res = AddWithCarry (sp_val, ~shifted, 1);
   9509 
   9510         EmulateInstruction::Context context;
   9511         context.type = eContextArithmetic;
   9512         RegisterInfo sp_reg;
   9513         GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg);
   9514         RegisterInfo dwarf_reg;
   9515         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, dwarf_reg);
   9516         context.SetRegisterRegisterOperands (sp_reg, dwarf_reg);
   9517 
   9518         if (!WriteCoreRegOptionalFlags(context, res.result, dwarf_r0 + d, setflags, res.carry_out, res.overflow))
   9519             return false;
   9520     }
   9521     return true;
   9522 }
   9523 
   9524 
   9525 // A8.6.7 ADD (register-shifted register)
   9526 bool
   9527 EmulateInstructionARM::EmulateADDRegShift (const uint32_t opcode, const ARMEncoding encoding)
   9528 {
   9529 #if 0
   9530     if ConditionPassed() then
   9531         EncodingSpecificOperations();
   9532         shift_n = UInt(R[s]<7:0>);
   9533         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9534         (result, carry, overflow) = AddWithCarry(R[n], shifted, 0);
   9535         R[d] = result;
   9536         if setflags then
   9537             APSR.N = result<31>;
   9538             APSR.Z = IsZeroBit(result);
   9539             APSR.C = carry;
   9540             APSR.V = overflow;
   9541 #endif
   9542 
   9543     bool success = false;
   9544 
   9545     if (ConditionPassed(opcode))
   9546     {
   9547         uint32_t d;
   9548         uint32_t n;
   9549         uint32_t m;
   9550         uint32_t s;
   9551         bool setflags;
   9552         ARM_ShifterType shift_t;
   9553 
   9554         switch (encoding)
   9555         {
   9556             case eEncodingA1:
   9557                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); s = UInt(Rs);
   9558                 d = Bits32 (opcode, 15, 12);
   9559                 n = Bits32 (opcode, 19, 16);
   9560                 m = Bits32 (opcode, 3, 0);
   9561                 s = Bits32 (opcode, 11, 8);
   9562 
   9563                 // setflags = (S == 1); shift_t = DecodeRegShift(type);
   9564                 setflags = BitIsSet (opcode, 20);
   9565                 shift_t = DecodeRegShift (Bits32 (opcode, 6, 5));
   9566 
   9567                 // if d == 15 || n == 15 || m == 15 || s == 15 then UNPREDICTABLE;
   9568                 if ((d == 15) || (m == 15) || (m == 15) || (s == 15))
   9569                     return false;
   9570                 break;
   9571 
   9572             default:
   9573                 return false;
   9574         }
   9575 
   9576         // shift_n = UInt(R[s]<7:0>);
   9577         uint32_t Rs = ReadCoreReg (s, &success);
   9578         if (!success)
   9579             return false;
   9580 
   9581         uint32_t shift_n = Bits32 (Rs, 7, 0);
   9582 
   9583         // shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9584         uint32_t Rm = ReadCoreReg (m, &success);
   9585         if (!success)
   9586             return false;
   9587 
   9588         uint32_t shifted = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   9589         if (!success)
   9590             return false;
   9591 
   9592         // (result, carry, overflow) = AddWithCarry(R[n], shifted, 0);
   9593         uint32_t Rn = ReadCoreReg (n, &success);
   9594         if (!success)
   9595             return false;
   9596 
   9597         AddWithCarryResult res = AddWithCarry (Rn, shifted, 0);
   9598 
   9599         // R[d] = result;
   9600         EmulateInstruction::Context context;
   9601         context.type = eContextArithmetic;
   9602         RegisterInfo reg_n;
   9603         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, reg_n);
   9604         RegisterInfo reg_m;
   9605         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, reg_m);
   9606 
   9607         context.SetRegisterRegisterOperands (reg_n, reg_m);
   9608 
   9609         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, res.result))
   9610             return false;
   9611 
   9612         // if setflags then
   9613             // APSR.N = result<31>;
   9614             // APSR.Z = IsZeroBit(result);
   9615             // APSR.C = carry;
   9616             // APSR.V = overflow;
   9617         if (setflags)
   9618             return WriteFlags (context, res.result, res.carry_out, res.overflow);
   9619     }
   9620     return true;
   9621 }
   9622 
   9623 // A8.6.213 SUB (register)
   9624 bool
   9625 EmulateInstructionARM::EmulateSUBReg (const uint32_t opcode, const ARMEncoding encoding)
   9626 {
   9627 #if 0
   9628     if ConditionPassed() then
   9629         EncodingSpecificOperations();
   9630         shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9631         (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), 1);
   9632         if d == 15 then // Can only occur for ARM encoding
   9633             ALUWritePC(result); // setflags is always FALSE here
   9634         else
   9635             R[d] = result;
   9636             if setflags then
   9637                 APSR.N = result<31>;
   9638                 APSR.Z = IsZeroBit(result);
   9639                 APSR.C = carry;
   9640                 APSR.V = overflow;
   9641 #endif
   9642 
   9643     bool success = false;
   9644 
   9645     if (ConditionPassed(opcode))
   9646     {
   9647         uint32_t d;
   9648         uint32_t n;
   9649         uint32_t m;
   9650         bool setflags;
   9651         ARM_ShifterType shift_t;
   9652         uint32_t shift_n;
   9653 
   9654         switch (encoding)
   9655         {
   9656             case eEncodingT1:
   9657                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = !InITBlock();
   9658                 d = Bits32 (opcode, 2, 0);
   9659                 n = Bits32 (opcode, 5, 3);
   9660                 m = Bits32 (opcode, 8, 6);
   9661                 setflags = !InITBlock();
   9662 
   9663                 // (shift_t, shift_n) = (SRType_LSL, 0);
   9664                 shift_t = SRType_LSL;
   9665                 shift_n = 0;
   9666 
   9667                 break;
   9668 
   9669             case eEncodingT2:
   9670                 // if Rd == 1111 && S == 1 then SEE CMP (register);
   9671                 // if Rn == 1101 then SEE SUB (SP minus register);
   9672                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = (S == 1);
   9673                 d = Bits32 (opcode, 11, 8);
   9674                 n = Bits32 (opcode, 19, 16);
   9675                 m = Bits32 (opcode, 3, 0);
   9676                 setflags = BitIsSet (opcode, 20);
   9677 
   9678                 // (shift_t, shift_n) = DecodeImmShift(type, imm3:imm2);
   9679                 shift_n = DecodeImmShiftThumb (opcode, shift_t);
   9680 
   9681                 // if d == 13 || (d == 15 && S == '0') || n == 15 || BadReg(m) then UNPREDICTABLE;
   9682                 if ((d == 13) || ((d == 15) && BitIsClear (opcode, 20)) || (n == 15) || BadReg (m))
   9683                     return false;
   9684 
   9685                 break;
   9686 
   9687             case eEncodingA1:
   9688                 // if Rn == 1101 then SEE SUB (SP minus register);
   9689                 // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = (S == 1);
   9690                 d = Bits32 (opcode, 15, 12);
   9691                 n = Bits32 (opcode, 19, 16);
   9692                 m = Bits32 (opcode, 3, 0);
   9693                 setflags = BitIsSet (opcode, 20);
   9694 
   9695                 // if Rd == 1111 && S == 1 then SEE SUBS PC, LR and related instructions;
   9696                 if ((d == 15) && setflags)
   9697                     EmulateSUBSPcLrEtc (opcode, encoding);
   9698 
   9699                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   9700                 shift_n = DecodeImmShiftARM (opcode, shift_t);
   9701 
   9702                 break;
   9703 
   9704             default:
   9705                 return false;
   9706         }
   9707 
   9708         // shifted = Shift(R[m], shift_t, shift_n, APSR.C);
   9709         uint32_t Rm = ReadCoreReg (m, &success);
   9710         if (!success)
   9711             return false;
   9712 
   9713         uint32_t shifted = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   9714         if (!success)
   9715             return false;
   9716 
   9717         // (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), 1);
   9718         uint32_t Rn = ReadCoreReg (n, &success);
   9719         if (!success)
   9720             return false;
   9721 
   9722         AddWithCarryResult res = AddWithCarry (Rn, ~shifted, 1);
   9723 
   9724         // if d == 15 then // Can only occur for ARM encoding
   9725             // ALUWritePC(result); // setflags is always FALSE here
   9726         // else
   9727             // R[d] = result;
   9728             // if setflags then
   9729                 // APSR.N = result<31>;
   9730                 // APSR.Z = IsZeroBit(result);
   9731                 // APSR.C = carry;
   9732                 // APSR.V = overflow;
   9733 
   9734         EmulateInstruction::Context context;
   9735         context.type = eContextArithmetic;
   9736         RegisterInfo reg_n;
   9737         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, reg_n);
   9738         RegisterInfo reg_m;
   9739         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, reg_m);
   9740         context.SetRegisterRegisterOperands (reg_n, reg_m);
   9741 
   9742         if (!WriteCoreRegOptionalFlags (context, res.result, dwarf_r0 + d, setflags, res.carry_out, res.overflow))
   9743             return false;
   9744     }
   9745     return true;
   9746 }
   9747 
   9748 // A8.6.202 STREX
   9749 // Store Register Exclusive calculates an address from a base register value and an immediate offset, and stores a
   9750 // word from a register to memory if the executing processor has exclusive access to the memory addressed.
   9751 bool
   9752 EmulateInstructionARM::EmulateSTREX (const uint32_t opcode, const ARMEncoding encoding)
   9753 {
   9754 #if 0
   9755     if ConditionPassed() then
   9756         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   9757         address = R[n] + imm32;
   9758         if ExclusiveMonitorsPass(address,4) then
   9759             MemA[address,4] = R[t];
   9760             R[d] = 0;
   9761         else
   9762             R[d] = 1;
   9763 #endif
   9764 
   9765     bool success = false;
   9766 
   9767     if (ConditionPassed(opcode))
   9768     {
   9769         uint32_t d;
   9770         uint32_t t;
   9771         uint32_t n;
   9772         uint32_t imm32;
   9773         const uint32_t addr_byte_size = GetAddressByteSize();
   9774 
   9775         switch (encoding)
   9776         {
   9777             case eEncodingT1:
   9778                 // d = UInt(Rd); t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8:00, 32);
   9779                 d = Bits32 (opcode, 11, 8);
   9780                 t = Bits32 (opcode, 15, 12);
   9781                 n = Bits32 (opcode, 19, 16);
   9782                 imm32 = Bits32 (opcode, 7, 0) << 2;
   9783 
   9784                 // if BadReg(d) || BadReg(t) || n == 15 then UNPREDICTABLE;
   9785                 if (BadReg (d) || BadReg (t) || (n == 15))
   9786                   return false;
   9787 
   9788                 // if d == n || d == t then UNPREDICTABLE;
   9789                 if ((d == n) || (d == t))
   9790                   return false;
   9791 
   9792                 break;
   9793 
   9794             case eEncodingA1:
   9795                 // d = UInt(Rd); t = UInt(Rt); n = UInt(Rn); imm32 = Zeros(32); // Zero offset
   9796                 d = Bits32 (opcode, 15, 12);
   9797                 t = Bits32 (opcode, 3, 0);
   9798                 n = Bits32 (opcode, 19, 16);
   9799                 imm32 = 0;
   9800 
   9801                 // if d == 15 || t == 15 || n == 15 then UNPREDICTABLE;
   9802                 if ((d == 15) || (t == 15) || (n == 15))
   9803                     return false;
   9804 
   9805                 // if d == n || d == t then UNPREDICTABLE;
   9806                 if ((d == n) || (d == t))
   9807                     return false;
   9808 
   9809                 break;
   9810 
   9811             default:
   9812                 return false;
   9813         }
   9814 
   9815         // address = R[n] + imm32;
   9816         uint32_t Rn = ReadCoreReg (n, &success);
   9817         if (!success)
   9818             return false;
   9819 
   9820         addr_t address = Rn + imm32;
   9821 
   9822         RegisterInfo base_reg;
   9823         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   9824         RegisterInfo data_reg;
   9825         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   9826         EmulateInstruction::Context context;
   9827         context.type = eContextRegisterStore;
   9828         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, imm32);
   9829 
   9830         // if ExclusiveMonitorsPass(address,4) then
   9831         // if (ExclusiveMonitorsPass (address, addr_byte_size)) -- For now, for the sake of emulation, we will say this
   9832         //                                                         always return true.
   9833         if (true)
   9834         {
   9835             // MemA[address,4] = R[t];
   9836             uint32_t Rt = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_r0 + t, 0, &success);
   9837             if (!success)
   9838                 return false;
   9839 
   9840             if (!MemAWrite (context, address, Rt, addr_byte_size))
   9841                 return false;
   9842 
   9843             // R[d] = 0;
   9844             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, 0))
   9845                 return false;
   9846         }
   9847         else
   9848         {
   9849             // R[d] = 1;
   9850             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, 1))
   9851                 return false;
   9852         }
   9853     }
   9854     return true;
   9855 }
   9856 
   9857 // A8.6.197 STRB (immediate, ARM)
   9858 bool
   9859 EmulateInstructionARM::EmulateSTRBImmARM (const uint32_t opcode, const ARMEncoding encoding)
   9860 {
   9861 #if 0
   9862     if ConditionPassed() then
   9863         EncodingSpecificOperations();
   9864         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   9865         address = if index then offset_addr else R[n];
   9866         MemU[address,1] = R[t]<7:0>;
   9867         if wback then R[n] = offset_addr;
   9868 #endif
   9869 
   9870     bool success = false;
   9871 
   9872     if (ConditionPassed(opcode))
   9873     {
   9874         uint32_t t;
   9875         uint32_t n;
   9876         uint32_t imm32;
   9877         bool index;
   9878         bool add;
   9879         bool wback;
   9880 
   9881         switch (encoding)
   9882         {
   9883             case eEncodingA1:
   9884                 // if P == 0 && W == 1 then SEE STRBT;
   9885                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   9886                 t = Bits32 (opcode, 15, 12);
   9887                 n = Bits32 (opcode, 19, 16);
   9888                 imm32 = Bits32 (opcode, 11, 0);
   9889 
   9890                 // index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   9891                 index = BitIsSet (opcode, 24);
   9892                 add = BitIsSet (opcode, 23);
   9893                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   9894 
   9895                 // if t == 15 then UNPREDICTABLE;
   9896                 if (t == 15)
   9897                     return false;
   9898 
   9899                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   9900                 if (wback && ((n == 15) || (n == t)))
   9901                     return false;
   9902 
   9903                 break;
   9904 
   9905             default:
   9906                 return false;
   9907         }
   9908 
   9909         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   9910         uint32_t Rn = ReadCoreReg (n, &success);
   9911         if (!success)
   9912             return false;
   9913 
   9914         addr_t offset_addr;
   9915         if (add)
   9916             offset_addr = Rn + imm32;
   9917         else
   9918             offset_addr = Rn - imm32;
   9919 
   9920         // address = if index then offset_addr else R[n];
   9921         addr_t address;
   9922         if (index)
   9923             address = offset_addr;
   9924         else
   9925             address = Rn;
   9926 
   9927         // MemU[address,1] = R[t]<7:0>;
   9928         uint32_t Rt = ReadCoreReg (t, &success);
   9929         if (!success)
   9930             return false;
   9931 
   9932         RegisterInfo base_reg;
   9933         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   9934         RegisterInfo data_reg;
   9935         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   9936         EmulateInstruction::Context context;
   9937         context.type = eContextRegisterStore;
   9938         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   9939 
   9940         if (!MemUWrite (context, address, Bits32 (Rt, 7, 0), 1))
   9941             return false;
   9942 
   9943         // if wback then R[n] = offset_addr;
   9944         if (wback)
   9945         {
   9946             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   9947                 return false;
   9948         }
   9949     }
   9950     return true;
   9951 }
   9952 
   9953 // A8.6.194 STR (immediate, ARM)
   9954 bool
   9955 EmulateInstructionARM::EmulateSTRImmARM (const uint32_t opcode, const ARMEncoding encoding)
   9956 {
   9957 #if 0
   9958     if ConditionPassed() then
   9959         EncodingSpecificOperations();
   9960         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   9961         address = if index then offset_addr else R[n];
   9962         MemU[address,4] = if t == 15 then PCStoreValue() else R[t];
   9963         if wback then R[n] = offset_addr;
   9964 #endif
   9965 
   9966     bool success = false;
   9967 
   9968     if (ConditionPassed(opcode))
   9969     {
   9970         uint32_t t;
   9971         uint32_t n;
   9972         uint32_t imm32;
   9973         bool index;
   9974         bool add;
   9975         bool wback;
   9976 
   9977         const uint32_t addr_byte_size = GetAddressByteSize();
   9978 
   9979         switch (encoding)
   9980         {
   9981             case eEncodingA1:
   9982                 // if P == 0 && W == 1 then SEE STRT;
   9983                 // if Rn == 1101 && P == 1 && U == 0 && W == 1 && imm12 == 000000000100 then SEE PUSH;
   9984                 // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32);
   9985                 t = Bits32 (opcode, 15, 12);
   9986                 n = Bits32 (opcode, 19, 16);
   9987                 imm32 = Bits32 (opcode, 11, 0);
   9988 
   9989                 // index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   9990                 index = BitIsSet (opcode, 24);
   9991                 add = BitIsSet (opcode, 23);
   9992                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   9993 
   9994                 // if wback && (n == 15 || n == t) then UNPREDICTABLE;
   9995                 if (wback && ((n == 15) || (n == t)))
   9996                     return false;
   9997 
   9998                 break;
   9999 
   10000             default:
   10001                 return false;
   10002         }
   10003 
   10004         // offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   10005         uint32_t Rn = ReadCoreReg (n, &success);
   10006         if (!success)
   10007             return false;
   10008 
   10009         addr_t offset_addr;
   10010         if (add)
   10011             offset_addr = Rn + imm32;
   10012         else
   10013             offset_addr = Rn - imm32;
   10014 
   10015         // address = if index then offset_addr else R[n];
   10016         addr_t address;
   10017         if (index)
   10018             address = offset_addr;
   10019         else
   10020             address = Rn;
   10021 
   10022         RegisterInfo base_reg;
   10023         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10024         RegisterInfo data_reg;
   10025         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   10026         EmulateInstruction::Context context;
   10027         context.type = eContextRegisterStore;
   10028         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   10029 
   10030         // MemU[address,4] = if t == 15 then PCStoreValue() else R[t];
   10031         uint32_t Rt = ReadCoreReg (t, &success);
   10032         if (!success)
   10033             return false;
   10034 
   10035         if (t == 15)
   10036         {
   10037             uint32_t pc_value = ReadCoreReg (PC_REG, &success);
   10038             if (!success)
   10039                 return false;
   10040 
   10041             if (!MemUWrite (context, address, pc_value, addr_byte_size))
   10042                 return false;
   10043         }
   10044         else
   10045         {
   10046             if (!MemUWrite (context, address, Rt, addr_byte_size))
   10047                   return false;
   10048         }
   10049 
   10050         // if wback then R[n] = offset_addr;
   10051         if (wback)
   10052         {
   10053             context.type = eContextAdjustBaseRegister;
   10054             context.SetImmediate (offset_addr);
   10055 
   10056             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   10057                 return false;
   10058         }
   10059     }
   10060     return true;
   10061 }
   10062 
   10063 // A8.6.66 LDRD (immediate)
   10064 // Load Register Dual (immediate) calculates an address from a base register value and an immediate offset, loads two
   10065 // words from memory, and writes them to two registers.  It can use offset, post-indexed, or pre-indexed addressing.
   10066 bool
   10067 EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEncoding encoding)
   10068 {
   10069 #if 0
   10070     if ConditionPassed() then
   10071         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   10072         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   10073         address = if index then offset_addr else R[n];
   10074         R[t] = MemA[address,4];
   10075         R[t2] = MemA[address+4,4];
   10076         if wback then R[n] = offset_addr;
   10077 #endif
   10078 
   10079     bool success = false;
   10080 
   10081     if (ConditionPassed(opcode))
   10082     {
   10083         uint32_t t;
   10084         uint32_t t2;
   10085         uint32_t n;
   10086         uint32_t imm32;
   10087         bool index;
   10088         bool add;
   10089         bool wback;
   10090 
   10091         switch (encoding)
   10092         {
   10093             case eEncodingT1:
   10094                 //if P == 0 && W == 0 then SEE Related encodings;
   10095                 //if Rn == 1111 then SEE LDRD (literal);
   10096                 //t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:00, 32);
   10097                 t = Bits32 (opcode, 15, 12);
   10098                 t2 = Bits32 (opcode, 11, 8);
   10099                 n = Bits32 (opcode, 19, 16);
   10100                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10101 
   10102                 //index = (P == 1); add = (U == 1); wback = (W == 1);
   10103                 index = BitIsSet (opcode, 24);
   10104                 add = BitIsSet (opcode, 23);
   10105                 wback = BitIsSet (opcode, 21);
   10106 
   10107                 //if wback && (n == t || n == t2) then UNPREDICTABLE;
   10108                 if (wback && ((n == t) || (n == t2)))
   10109                     return false;
   10110 
   10111                 //if BadReg(t) || BadReg(t2) || t == t2 then UNPREDICTABLE;
   10112                 if (BadReg (t) || BadReg (t2) || (t == t2))
   10113                     return false;
   10114 
   10115                 break;
   10116 
   10117             case eEncodingA1:
   10118                 //if Rn == 1111 then SEE LDRD (literal);
   10119                 //if Rt<0> == 1 then UNPREDICTABLE;
   10120                 //t = UInt(Rt); t2 = t+1; n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32);
   10121                 t = Bits32 (opcode, 15, 12);
   10122                 if (BitIsSet (t, 0))
   10123                     return false;
   10124                 t2 = t + 1;
   10125                 n = Bits32 (opcode, 19, 16);
   10126                 imm32 = (Bits32 (opcode, 11, 8) << 4) | Bits32 (opcode, 3, 0);
   10127 
   10128                 //index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   10129                 index = BitIsSet (opcode, 24);
   10130                 add = BitIsSet (opcode, 23);
   10131                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   10132 
   10133                 //if P == 0 && W == 1 then UNPREDICTABLE;
   10134                 if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21))
   10135                     return false;
   10136 
   10137                 //if wback && (n == t || n == t2) then UNPREDICTABLE;
   10138                 if (wback && ((n == t) || (n == t2)))
   10139                     return false;
   10140 
   10141                 //if t2 == 15 then UNPREDICTABLE;
   10142                 if (t2 == 15)
   10143                     return false;
   10144 
   10145                 break;
   10146 
   10147             default:
   10148                 return false;
   10149         }
   10150 
   10151         //offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   10152         uint32_t Rn = ReadCoreReg (n, &success);
   10153         if (!success)
   10154             return false;
   10155 
   10156         addr_t offset_addr;
   10157         if (add)
   10158                   offset_addr = Rn + imm32;
   10159         else
   10160             offset_addr = Rn - imm32;
   10161 
   10162         //address = if index then offset_addr else R[n];
   10163         addr_t address;
   10164         if (index)
   10165             address = offset_addr;
   10166         else
   10167             address = Rn;
   10168 
   10169         //R[t] = MemA[address,4];
   10170         RegisterInfo base_reg;
   10171         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10172 
   10173         EmulateInstruction::Context context;
   10174         context.type = eContextRegisterLoad;
   10175         context.SetRegisterPlusOffset (base_reg, address - Rn);
   10176 
   10177         const uint32_t addr_byte_size = GetAddressByteSize();
   10178         uint32_t data = MemARead (context, address, addr_byte_size, 0, &success);
   10179         if (!success)
   10180             return false;
   10181 
   10182         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   10183             return false;
   10184 
   10185         //R[t2] = MemA[address+4,4];
   10186 
   10187         context.SetRegisterPlusOffset (base_reg, (address + 4) - Rn);
   10188         data = MemARead (context, address + 4, addr_byte_size, 0, &success);
   10189         if (!success)
   10190             return false;
   10191 
   10192         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t2, data))
   10193             return false;
   10194 
   10195         //if wback then R[n] = offset_addr;
   10196         if (wback)
   10197         {
   10198             context.type = eContextAdjustBaseRegister;
   10199             context.SetAddress (offset_addr);
   10200 
   10201             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   10202                 return false;
   10203         }
   10204     }
   10205     return true;
   10206 }
   10207 
   10208 // A8.6.68 LDRD (register)
   10209 // Load Register Dual (register) calculates an address from a base register value and a register offset, loads two
   10210 // words from memory, and writes them to two registers.  It can use offset, post-indexed or pre-indexed addressing.
   10211 bool
   10212 EmulateInstructionARM::EmulateLDRDRegister (const uint32_t opcode, const ARMEncoding encoding)
   10213 {
   10214 #if 0
   10215     if ConditionPassed() then
   10216         EncodingSpecificOperations();
   10217         offset_addr = if add then (R[n] + R[m]) else (R[n] - R[m]);
   10218         address = if index then offset_addr else R[n];
   10219         R[t] = MemA[address,4];
   10220         R[t2] = MemA[address+4,4];
   10221         if wback then R[n] = offset_addr;
   10222 #endif
   10223 
   10224     bool success = false;
   10225 
   10226     if (ConditionPassed(opcode))
   10227     {
   10228         uint32_t t;
   10229         uint32_t t2;
   10230         uint32_t n;
   10231         uint32_t m;
   10232         bool index;
   10233         bool add;
   10234         bool wback;
   10235 
   10236         switch (encoding)
   10237         {
   10238             case eEncodingA1:
   10239                 // if Rt<0> == 1 then UNPREDICTABLE;
   10240                 // t = UInt(Rt); t2 = t+1; n = UInt(Rn); m = UInt(Rm);
   10241                 t = Bits32 (opcode, 15, 12);
   10242                 if (BitIsSet (t, 0))
   10243                     return false;
   10244                 t2 = t + 1;
   10245                 n = Bits32 (opcode, 19, 16);
   10246                 m = Bits32 (opcode, 3, 0);
   10247 
   10248                 // index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   10249                 index = BitIsSet (opcode, 24);
   10250                 add = BitIsSet (opcode, 23);
   10251                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   10252 
   10253                 // if P == 0 && W == 1 then UNPREDICTABLE;
   10254                   if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21))
   10255                   return false;
   10256 
   10257                 // if t2 == 15 || m == 15 || m == t || m == t2 then UNPREDICTABLE;
   10258                   if ((t2 == 15) || (m == 15) || (m == t) || (m == t2))
   10259                   return false;
   10260 
   10261                 // if wback && (n == 15 || n == t || n == t2) then UNPREDICTABLE;
   10262                   if (wback && ((n == 15) || (n == t) || (n == t2)))
   10263                   return false;
   10264 
   10265                 // if ArchVersion() < 6 && wback && m == n then UNPREDICTABLE;
   10266                 if ((ArchVersion() < 6) && wback && (m == n))
   10267                   return false;
   10268                 break;
   10269 
   10270             default:
   10271                 return false;
   10272         }
   10273 
   10274         uint32_t Rn = ReadCoreReg (n, &success);
   10275         if (!success)
   10276             return false;
   10277         RegisterInfo base_reg;
   10278         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10279 
   10280         uint32_t Rm = ReadCoreReg (m, &success);
   10281         if (!success)
   10282             return false;
   10283         RegisterInfo offset_reg;
   10284         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   10285 
   10286         // offset_addr = if add then (R[n] + R[m]) else (R[n] - R[m]);
   10287         addr_t offset_addr;
   10288         if (add)
   10289             offset_addr = Rn + Rm;
   10290         else
   10291             offset_addr = Rn - Rm;
   10292 
   10293         // address = if index then offset_addr else R[n];
   10294         addr_t address;
   10295         if (index)
   10296             address = offset_addr;
   10297         else
   10298             address = Rn;
   10299 
   10300         EmulateInstruction::Context context;
   10301         context.type = eContextRegisterLoad;
   10302         context.SetRegisterPlusIndirectOffset (base_reg, offset_reg);
   10303 
   10304         // R[t] = MemA[address,4];
   10305         const uint32_t addr_byte_size = GetAddressByteSize();
   10306         uint32_t data = MemARead (context, address, addr_byte_size, 0, &success);
   10307         if (!success)
   10308             return false;
   10309 
   10310         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t, data))
   10311             return false;
   10312 
   10313         // R[t2] = MemA[address+4,4];
   10314 
   10315         data = MemARead (context, address + 4, addr_byte_size, 0, &success);
   10316         if (!success)
   10317             return false;
   10318 
   10319         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + t2, data))
   10320             return false;
   10321 
   10322         // if wback then R[n] = offset_addr;
   10323         if (wback)
   10324         {
   10325             context.type = eContextAdjustBaseRegister;
   10326             context.SetAddress (offset_addr);
   10327 
   10328             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   10329                 return false;
   10330         }
   10331     }
   10332     return true;
   10333 }
   10334 
   10335 // A8.6.200 STRD (immediate)
   10336 // Store Register Dual (immediate) calculates an address from a base register value and an immediate offset, and
   10337 // stores two words from two registers to memory.  It can use offset, post-indexed, or pre-indexed addressing.
   10338 bool
   10339 EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding encoding)
   10340 {
   10341 #if 0
   10342     if ConditionPassed() then
   10343         EncodingSpecificOperations(); NullCheckIfThumbEE(n);
   10344         offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   10345         address = if index then offset_addr else R[n];
   10346         MemA[address,4] = R[t];
   10347         MemA[address+4,4] = R[t2];
   10348         if wback then R[n] = offset_addr;
   10349 #endif
   10350 
   10351     bool success = false;
   10352 
   10353     if (ConditionPassed(opcode))
   10354     {
   10355         uint32_t t;
   10356         uint32_t t2;
   10357         uint32_t n;
   10358         uint32_t imm32;
   10359         bool index;
   10360         bool add;
   10361         bool wback;
   10362 
   10363         switch (encoding)
   10364         {
   10365             case eEncodingT1:
   10366                 // if P == 0 && W == 0 then SEE Related encodings;
   10367                 // t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:00, 32);
   10368                 t = Bits32 (opcode, 15, 12);
   10369                 t2 = Bits32 (opcode, 11, 8);
   10370                 n = Bits32 (opcode, 19, 16);
   10371                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10372 
   10373                 // index = (P == 1); add = (U == 1); wback = (W == 1);
   10374                 index = BitIsSet (opcode, 24);
   10375                 add = BitIsSet (opcode, 23);
   10376                 wback = BitIsSet (opcode, 21);
   10377 
   10378                 // if wback && (n == t || n == t2) then UNPREDICTABLE;
   10379                 if (wback && ((n == t) || (n == t2)))
   10380                     return false;
   10381 
   10382                 // if n == 15 || BadReg(t) || BadReg(t2) then UNPREDICTABLE;
   10383                 if ((n == 15) || BadReg (t) || BadReg (t2))
   10384                     return false;
   10385 
   10386                 break;
   10387 
   10388             case eEncodingA1:
   10389                 // if Rt<0> == 1 then UNPREDICTABLE;
   10390                 // t = UInt(Rt); t2 = t+1; n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32);
   10391                 t = Bits32 (opcode, 15, 12);
   10392                 if (BitIsSet (t, 0))
   10393                     return false;
   10394 
   10395                 t2 = t + 1;
   10396                 n = Bits32 (opcode, 19, 16);
   10397                 imm32 = (Bits32 (opcode, 11, 8) << 4) | Bits32 (opcode, 3, 0);
   10398 
   10399                 // index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   10400                 index = BitIsSet (opcode, 24);
   10401                 add = BitIsSet (opcode, 23);
   10402                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   10403 
   10404                 // if P == 0 && W == 1 then UNPREDICTABLE;
   10405                 if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21))
   10406                     return false;
   10407 
   10408                 // if wback && (n == 15 || n == t || n == t2) then UNPREDICTABLE;
   10409                 if (wback && ((n == 15) || (n == t) || (n == t2)))
   10410                     return false;
   10411 
   10412                 // if t2 == 15 then UNPREDICTABLE;
   10413                 if (t2 == 15)
   10414                     return false;
   10415 
   10416                 break;
   10417 
   10418             default:
   10419                 return false;
   10420         }
   10421 
   10422         RegisterInfo base_reg;
   10423         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10424 
   10425         uint32_t Rn = ReadCoreReg (n, &success);
   10426         if (!success)
   10427             return false;
   10428 
   10429         //offset_addr = if add then (R[n] + imm32) else (R[n] - imm32);
   10430         addr_t offset_addr;
   10431         if (add)
   10432             offset_addr = Rn + imm32;
   10433         else
   10434             offset_addr = Rn - imm32;
   10435 
   10436         //address = if index then offset_addr else R[n];
   10437         addr_t address;
   10438         if (index)
   10439             address = offset_addr;
   10440         else
   10441             address = Rn;
   10442 
   10443         //MemA[address,4] = R[t];
   10444         RegisterInfo data_reg;
   10445         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   10446 
   10447         uint32_t data = ReadCoreReg (t, &success);
   10448         if (!success)
   10449             return false;
   10450 
   10451         EmulateInstruction::Context context;
   10452         context.type = eContextRegisterStore;
   10453         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   10454 
   10455         const uint32_t addr_byte_size = GetAddressByteSize();
   10456 
   10457         if (!MemAWrite (context, address, data, addr_byte_size))
   10458             return false;
   10459 
   10460         //MemA[address+4,4] = R[t2];
   10461         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t2, data_reg);
   10462         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, (address + 4) - Rn);
   10463 
   10464         data = ReadCoreReg (t2, &success);
   10465         if (!success)
   10466             return false;
   10467 
   10468         if (!MemAWrite (context, address + 4, data, addr_byte_size))
   10469             return false;
   10470 
   10471         //if wback then R[n] = offset_addr;
   10472         if (wback)
   10473         {
   10474             context.type = eContextAdjustBaseRegister;
   10475             context.SetAddress (offset_addr);
   10476 
   10477             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   10478                 return false;
   10479         }
   10480     }
   10481     return true;
   10482 }
   10483 
   10484 
   10485 // A8.6.201 STRD (register)
   10486 bool
   10487 EmulateInstructionARM::EmulateSTRDReg (const uint32_t opcode, const ARMEncoding encoding)
   10488 {
   10489 #if 0
   10490     if ConditionPassed() then
   10491         EncodingSpecificOperations();
   10492         offset_addr = if add then (R[n] + R[m]) else (R[n] - R[m]);
   10493         address = if index then offset_addr else R[n];
   10494         MemA[address,4] = R[t];
   10495         MemA[address+4,4] = R[t2];
   10496         if wback then R[n] = offset_addr;
   10497 #endif
   10498 
   10499     bool success = false;
   10500 
   10501     if (ConditionPassed(opcode))
   10502     {
   10503         uint32_t t;
   10504         uint32_t t2;
   10505         uint32_t n;
   10506         uint32_t m;
   10507         bool index;
   10508         bool add;
   10509         bool wback;
   10510 
   10511         switch (encoding)
   10512         {
   10513             case eEncodingA1:
   10514                 // if Rt<0> == 1 then UNPREDICTABLE;
   10515                 // t = UInt(Rt); t2 = t+1; n = UInt(Rn); m = UInt(Rm);
   10516                 t = Bits32 (opcode, 15, 12);
   10517                 if (BitIsSet (t, 0))
   10518                    return false;
   10519 
   10520                 t2 = t+1;
   10521                 n = Bits32 (opcode, 19, 16);
   10522                 m = Bits32 (opcode, 3, 0);
   10523 
   10524                 // index = (P == 1); add = (U == 1); wback = (P == 0) || (W == 1);
   10525                 index = BitIsSet (opcode, 24);
   10526                 add = BitIsSet (opcode, 23);
   10527                 wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21);
   10528 
   10529                 // if P == 0 && W == 1 then UNPREDICTABLE;
   10530                 if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21))
   10531                    return false;
   10532 
   10533                 // if t2 == 15 || m == 15 then UNPREDICTABLE;
   10534                 if ((t2 == 15) || (m == 15))
   10535                    return false;
   10536 
   10537                 // if wback && (n == 15 || n == t || n == t2) then UNPREDICTABLE;
   10538                 if (wback && ((n == 15) || (n == t) || (n == t2)))
   10539                    return false;
   10540 
   10541                 // if ArchVersion() < 6 && wback && m == n then UNPREDICTABLE;
   10542                 if ((ArchVersion() < 6) && wback && (m == n))
   10543                    return false;
   10544 
   10545                 break;
   10546 
   10547             default:
   10548                 return false;
   10549         }
   10550 
   10551         RegisterInfo base_reg;
   10552         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10553         RegisterInfo offset_reg;
   10554         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + m, offset_reg);
   10555         RegisterInfo data_reg;
   10556 
   10557         uint32_t Rn = ReadCoreReg (n, &success);
   10558         if (!success)
   10559             return false;
   10560 
   10561         uint32_t Rm = ReadCoreReg (m, &success);
   10562         if (!success)
   10563             return false;
   10564 
   10565         // offset_addr = if add then (R[n] + R[m]) else (R[n] - R[m]);
   10566         addr_t offset_addr;
   10567         if (add)
   10568             offset_addr = Rn + Rm;
   10569         else
   10570             offset_addr = Rn - Rm;
   10571 
   10572         // address = if index then offset_addr else R[n];
   10573         addr_t address;
   10574         if (index)
   10575             address = offset_addr;
   10576         else
   10577             address = Rn;
   10578                           // MemA[address,4] = R[t];
   10579         uint32_t Rt = ReadCoreReg (t, &success);
   10580         if (!success)
   10581             return false;
   10582 
   10583         EmulateInstruction::Context context;
   10584         context.type = eContextRegisterStore;
   10585         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg);
   10586         context.SetRegisterToRegisterPlusIndirectOffset (base_reg, offset_reg, data_reg);
   10587 
   10588         const uint32_t addr_byte_size = GetAddressByteSize();
   10589 
   10590         if (!MemAWrite (context, address, Rt, addr_byte_size))
   10591             return false;
   10592 
   10593         // MemA[address+4,4] = R[t2];
   10594         uint32_t Rt2 = ReadCoreReg (t2, &success);
   10595         if (!success)
   10596             return false;
   10597 
   10598         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t2, data_reg);
   10599 
   10600         context.SetRegisterToRegisterPlusIndirectOffset (base_reg, offset_reg, data_reg);
   10601 
   10602         if (!MemAWrite (context, address + 4, Rt2, addr_byte_size))
   10603             return false;
   10604 
   10605         // if wback then R[n] = offset_addr;
   10606         if (wback)
   10607         {
   10608             context.type = eContextAdjustBaseRegister;
   10609             context.SetAddress (offset_addr);
   10610 
   10611             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr))
   10612                 return false;
   10613 
   10614         }
   10615     }
   10616     return true;
   10617 }
   10618 
   10619 // A8.6.319 VLDM
   10620 // Vector Load Multiple loads multiple extension registers from consecutive memory locations using an address from
   10621 // an ARM core register.
   10622 bool
   10623 EmulateInstructionARM::EmulateVLDM (const uint32_t opcode, const ARMEncoding encoding)
   10624 {
   10625 #if 0
   10626     if ConditionPassed() then
   10627         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(n);
   10628         address = if add then R[n] else R[n]-imm32;
   10629         if wback then R[n] = if add then R[n]+imm32 else R[n]-imm32;
   10630         for r = 0 to regs-1
   10631             if single_regs then
   10632                 S[d+r] = MemA[address,4]; address = address+4;
   10633             else
   10634                 word1 = MemA[address,4]; word2 = MemA[address+4,4]; address = address+8;
   10635                 // Combine the word-aligned words in the correct order for current endianness.
   10636                 D[d+r] = if BigEndian() then word1:word2 else word2:word1;
   10637 #endif
   10638 
   10639     bool success = false;
   10640 
   10641     if (ConditionPassed(opcode))
   10642     {
   10643         bool single_regs;
   10644         bool add;
   10645         bool wback;
   10646         uint32_t d;
   10647         uint32_t n;
   10648         uint32_t imm32;
   10649         uint32_t regs;
   10650 
   10651         switch (encoding)
   10652         {
   10653             case eEncodingT1:
   10654             case eEncodingA1:
   10655                 // if P == 0 && U == 0 && W == 0 then SEE Related encodings;
   10656                 // if P == 0 && U == 1 && W == 1 && Rn == 1101 then SEE VPOP;
   10657                 // if P == 1 && W == 0 then SEE VLDR;
   10658                 // if P == U && W == 1 then UNDEFINED;
   10659                 if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21))
   10660                     return false;
   10661 
   10662                 // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !)
   10663                 // single_regs = FALSE; add = (U == 1); wback = (W == 1);
   10664                 single_regs = false;
   10665                 add = BitIsSet (opcode, 23);
   10666                 wback = BitIsSet (opcode, 21);
   10667 
   10668                 // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:00, 32);
   10669                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   10670                 n = Bits32 (opcode, 19, 16);
   10671                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10672 
   10673                 // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see FLDMX.
   10674                 regs = Bits32 (opcode, 7, 0) / 2;
   10675 
   10676                 // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE;
   10677                 if (n == 15 && (wback || CurrentInstrSet() != eModeARM))
   10678                     return false;
   10679 
   10680                 // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   10681                 if ((regs == 0) || (regs > 16) || ((d + regs) > 32))
   10682                     return false;
   10683 
   10684                 break;
   10685 
   10686             case eEncodingT2:
   10687             case eEncodingA2:
   10688                 // if P == 0 && U == 0 && W == 0 then SEE Related encodings;
   10689                 // if P == 0 && U == 1 && W == 1 && Rn == 1101 then SEE VPOP;
   10690                 // if P == 1 && W == 0 then SEE VLDR;
   10691                 // if P == U && W == 1 then UNDEFINED;
   10692                 if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21))
   10693                     return false;
   10694 
   10695                 // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !)
   10696                 // single_regs = TRUE; add = (U == 1); wback = (W == 1); d = UInt(Vd:D); n = UInt(Rn);
   10697                 single_regs = true;
   10698                 add = BitIsSet (opcode, 23);
   10699                 wback = BitIsSet (opcode, 21);
   10700                 d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22);
   10701                 n = Bits32 (opcode, 19, 16);
   10702 
   10703                 // imm32 = ZeroExtend(imm8:00, 32); regs = UInt(imm8);
   10704                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10705                 regs = Bits32 (opcode, 7, 0);
   10706 
   10707                 // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE;
   10708                 if ((n == 15) && (wback || (CurrentInstrSet() != eModeARM)))
   10709                     return false;
   10710 
   10711                 // if regs == 0 || (d+regs) > 32 then UNPREDICTABLE;
   10712                 if ((regs == 0) || ((d + regs) > 32))
   10713                     return false;
   10714                 break;
   10715 
   10716             default:
   10717                 return false;
   10718         }
   10719 
   10720         RegisterInfo base_reg;
   10721         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10722 
   10723         uint32_t Rn = ReadCoreReg (n, &success);
   10724         if (!success)
   10725             return false;
   10726 
   10727         // address = if add then R[n] else R[n]-imm32;
   10728         addr_t address;
   10729         if (add)
   10730             address = Rn;
   10731         else
   10732             address = Rn - imm32;
   10733 
   10734         // if wback then R[n] = if add then R[n]+imm32 else R[n]-imm32;
   10735         EmulateInstruction::Context context;
   10736 
   10737         if (wback)
   10738         {
   10739             uint32_t value;
   10740             if (add)
   10741                 value = Rn + imm32;
   10742             else
   10743                 value = Rn - imm32;
   10744 
   10745             context.type = eContextAdjustBaseRegister;
   10746             context.SetImmediateSigned (value - Rn);
   10747             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, value))
   10748                 return false;
   10749 
   10750         }
   10751 
   10752         const uint32_t addr_byte_size = GetAddressByteSize();
   10753         uint32_t start_reg = single_regs ? dwarf_s0 : dwarf_d0;
   10754 
   10755         context.type = eContextRegisterLoad;
   10756 
   10757         // for r = 0 to regs-1
   10758         for (uint32_t r = 0; r < regs; ++r)
   10759         {
   10760             if (single_regs)
   10761             {
   10762                 // S[d+r] = MemA[address,4]; address = address+4;
   10763                 context.SetRegisterPlusOffset (base_reg, address - Rn);
   10764 
   10765                 uint32_t data = MemARead (context, address, addr_byte_size, 0, &success);
   10766                 if (!success)
   10767                     return false;
   10768 
   10769                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, start_reg + d + r, data))
   10770                     return false;
   10771 
   10772                 address = address + 4;
   10773             }
   10774             else
   10775             {
   10776                 // word1 = MemA[address,4]; word2 = MemA[address+4,4]; address = address+8;
   10777                 context.SetRegisterPlusOffset (base_reg, address - Rn);
   10778                 uint32_t word1 = MemARead (context, address, addr_byte_size, 0, &success);
   10779                 if (!success)
   10780                     return false;
   10781 
   10782                 context.SetRegisterPlusOffset (base_reg, (address + 4) - Rn);
   10783                 uint32_t word2 = MemARead (context, address + 4, addr_byte_size, 0, &success);
   10784                 if (!success)
   10785                     return false;
   10786 
   10787                 address = address + 8;
   10788                 // // Combine the word-aligned words in the correct order for current endianness.
   10789                 // D[d+r] = if BigEndian() then word1:word2 else word2:word1;
   10790                 uint64_t data;
   10791                 if (GetByteOrder() == eByteOrderBig)
   10792                 {
   10793                     data = word1;
   10794                     data = (data << 32) | word2;
   10795                 }
   10796                 else
   10797                 {
   10798                     data = word2;
   10799                     data = (data << 32) | word1;
   10800                 }
   10801 
   10802                 if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, start_reg + d + r, data))
   10803                     return false;
   10804             }
   10805         }
   10806     }
   10807     return true;
   10808 }
   10809 
   10810 // A8.6.399 VSTM
   10811 // Vector Store Multiple stores multiple extension registers to consecutive memory locations using an address from an
   10812 // ARM core register.
   10813 bool
   10814 EmulateInstructionARM::EmulateVSTM (const uint32_t opcode, const ARMEncoding encoding)
   10815 {
   10816 #if 0
   10817     if ConditionPassed() then
   10818         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(n);
   10819         address = if add then R[n] else R[n]-imm32;
   10820         if wback then R[n] = if add then R[n]+imm32 else R[n]-imm32;
   10821         for r = 0 to regs-1
   10822             if single_regs then
   10823                 MemA[address,4] = S[d+r]; address = address+4;
   10824             else
   10825                 // Store as two word-aligned words in the correct order for current endianness.
   10826                 MemA[address,4] = if BigEndian() then D[d+r]<63:32> else D[d+r]<31:0>;
   10827                 MemA[address+4,4] = if BigEndian() then D[d+r]<31:0> else D[d+r]<63:32>;
   10828                 address = address+8;
   10829 #endif
   10830 
   10831     bool success = false;
   10832 
   10833     if (ConditionPassed (opcode))
   10834     {
   10835         bool single_regs;
   10836         bool add;
   10837         bool wback;
   10838         uint32_t d;
   10839         uint32_t n;
   10840         uint32_t imm32;
   10841         uint32_t regs;
   10842 
   10843         switch (encoding)
   10844         {
   10845             case eEncodingT1:
   10846             case eEncodingA1:
   10847                 // if P == 0 && U == 0 && W == 0 then SEE Related encodings;
   10848                 // if P == 1 && U == 0 && W == 1 && Rn == 1101 then SEE VPUSH;
   10849                 // if P == 1 && W == 0 then SEE VSTR;
   10850                 // if P == U && W == 1 then UNDEFINED;
   10851                 if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21))
   10852                     return false;
   10853 
   10854                 // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !)
   10855                 // single_regs = FALSE; add = (U == 1); wback = (W == 1);
   10856                 single_regs = false;
   10857                 add = BitIsSet (opcode, 23);
   10858                 wback = BitIsSet (opcode, 21);
   10859 
   10860                 // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:00, 32);
   10861                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   10862                 n = Bits32 (opcode, 19, 16);
   10863                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10864 
   10865                 // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see FSTMX.
   10866                 regs = Bits32 (opcode, 7, 0) / 2;
   10867 
   10868                 // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE;
   10869                 if ((n == 15) && (wback || (CurrentInstrSet() != eModeARM)))
   10870                     return false;
   10871 
   10872                 // if regs == 0 || regs > 16 || (d+regs) > 32 then UNPREDICTABLE;
   10873                 if ((regs == 0) || (regs > 16) || ((d + regs) > 32))
   10874                     return false;
   10875 
   10876                 break;
   10877 
   10878             case eEncodingT2:
   10879             case eEncodingA2:
   10880                 // if P == 0 && U == 0 && W == 0 then SEE Related encodings;
   10881                 // if P == 1 && U == 0 && W == 1 && Rn == 1101 then SEE VPUSH;
   10882                 // if P == 1 && W == 0 then SEE VSTR;
   10883                 // if P == U && W == 1 then UNDEFINED;
   10884                 if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21))
   10885                     return false;
   10886 
   10887                 // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !)
   10888                 // single_regs = TRUE; add = (U == 1); wback = (W == 1); d = UInt(Vd:D); n = UInt(Rn);
   10889                 single_regs = true;
   10890                 add = BitIsSet (opcode, 23);
   10891                 wback = BitIsSet (opcode, 21);
   10892                 d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22);
   10893                 n = Bits32 (opcode, 19, 16);
   10894 
   10895                 // imm32 = ZeroExtend(imm8:00, 32); regs = UInt(imm8);
   10896                 imm32 = Bits32 (opcode, 7, 0) << 2;
   10897                 regs = Bits32 (opcode, 7, 0);
   10898 
   10899                 // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE;
   10900                 if ((n == 15) && (wback || (CurrentInstrSet () != eModeARM)))
   10901                     return false;
   10902 
   10903                 // if regs == 0 || (d+regs) > 32 then UNPREDICTABLE;
   10904                 if ((regs == 0) || ((d + regs) > 32))
   10905                     return false;
   10906 
   10907                 break;
   10908 
   10909             default:
   10910                 return false;
   10911         }
   10912 
   10913         RegisterInfo base_reg;
   10914         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   10915 
   10916         uint32_t Rn = ReadCoreReg (n, &success);
   10917         if (!success)
   10918             return false;
   10919 
   10920         // address = if add then R[n] else R[n]-imm32;
   10921         addr_t address;
   10922         if (add)
   10923             address = Rn;
   10924         else
   10925             address = Rn - imm32;
   10926 
   10927         EmulateInstruction::Context context;
   10928         // if wback then R[n] = if add then R[n]+imm32 else R[n]-imm32;
   10929         if (wback)
   10930         {
   10931             uint32_t value;
   10932             if (add)
   10933                 value = Rn + imm32;
   10934             else
   10935                 value = Rn - imm32;
   10936 
   10937             context.type = eContextAdjustBaseRegister;
   10938             context.SetRegisterPlusOffset (base_reg, value - Rn);
   10939 
   10940             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, value))
   10941                 return false;
   10942         }
   10943 
   10944         const uint32_t addr_byte_size = GetAddressByteSize();
   10945         uint32_t start_reg = single_regs ? dwarf_s0 : dwarf_d0;
   10946 
   10947         context.type = eContextRegisterStore;
   10948         // for r = 0 to regs-1
   10949         for (uint32_t r = 0; r < regs; ++r)
   10950         {
   10951 
   10952             if (single_regs)
   10953             {
   10954                 // MemA[address,4] = S[d+r]; address = address+4;
   10955                 uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, start_reg + d + r, 0, &success);
   10956                 if (!success)
   10957                     return false;
   10958 
   10959                 RegisterInfo data_reg;
   10960                 GetRegisterInfo (eRegisterKindDWARF, start_reg + d + r, data_reg);
   10961                 context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   10962                 if (!MemAWrite (context, address, data, addr_byte_size))
   10963                     return false;
   10964 
   10965                 address = address + 4;
   10966             }
   10967             else
   10968             {
   10969                 // // Store as two word-aligned words in the correct order for current endianness.
   10970                 // MemA[address,4] = if BigEndian() then D[d+r]<63:32> else D[d+r]<31:0>;
   10971                 // MemA[address+4,4] = if BigEndian() then D[d+r]<31:0> else D[d+r]<63:32>;
   10972                 uint64_t data = ReadRegisterUnsigned (eRegisterKindDWARF, start_reg + d + r, 0, &success);
   10973                 if (!success)
   10974                     return false;
   10975 
   10976                 RegisterInfo data_reg;
   10977                 GetRegisterInfo (eRegisterKindDWARF, start_reg + d + r, data_reg);
   10978 
   10979                 if (GetByteOrder() == eByteOrderBig)
   10980                 {
   10981                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   10982                     if (!MemAWrite (context, address, Bits64 (data, 63, 32), addr_byte_size))
   10983                         return false;
   10984 
   10985                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, (address + 4) - Rn);
   10986                     if (!MemAWrite (context, address+ 4, Bits64 (data, 31, 0), addr_byte_size))
   10987                         return false;
   10988                 }
   10989                 else
   10990                 {
   10991                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   10992                     if (!MemAWrite (context, address, Bits64 (data, 31, 0), addr_byte_size))
   10993                         return false;
   10994 
   10995                     context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, (address + 4) - Rn);
   10996                     if (!MemAWrite (context, address + 4, Bits64 (data, 63, 32), addr_byte_size))
   10997                         return false;
   10998                 }
   10999                 // address = address+8;
   11000                 address = address + 8;
   11001             }
   11002         }
   11003     }
   11004     return true;
   11005 }
   11006 
   11007 // A8.6.320
   11008 // This instruciton loads a single extension register fronm memory, using an address from an ARM core register, with
   11009 // an optional offset.
   11010 bool
   11011 EmulateInstructionARM::EmulateVLDR (const uint32_t opcode, ARMEncoding encoding)
   11012 {
   11013 #if 0
   11014     if ConditionPassed() then
   11015         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(n);
   11016         base = if n == 15 then Align(PC,4) else R[n];
   11017         address = if add then (base + imm32) else (base - imm32);
   11018         if single_reg then
   11019             S[d] = MemA[address,4];
   11020         else
   11021             word1 = MemA[address,4]; word2 = MemA[address+4,4];
   11022             // Combine the word-aligned words in the correct order for current endianness.
   11023             D[d] = if BigEndian() then word1:word2 else word2:word1;
   11024 #endif
   11025 
   11026     bool success = false;
   11027 
   11028     if (ConditionPassed (opcode))
   11029     {
   11030         bool single_reg;
   11031         bool add;
   11032         uint32_t imm32;
   11033         uint32_t d;
   11034         uint32_t n;
   11035 
   11036         switch (encoding)
   11037         {
   11038             case eEncodingT1:
   11039             case eEncodingA1:
   11040                 // single_reg = FALSE; add = (U == 1); imm32 = ZeroExtend(imm8:00, 32);
   11041                 single_reg = false;
   11042                 add = BitIsSet (opcode, 23);
   11043                 imm32 = Bits32 (opcode, 7, 0) << 2;
   11044 
   11045                 // d = UInt(D:Vd); n = UInt(Rn);
   11046                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11047                 n = Bits32 (opcode, 19, 16);
   11048 
   11049                 break;
   11050 
   11051             case eEncodingT2:
   11052             case eEncodingA2:
   11053                 // single_reg = TRUE; add = (U == 1); imm32 = ZeroExtend(imm8:00, 32);
   11054                 single_reg = true;
   11055                 add = BitIsSet (opcode, 23);
   11056                 imm32 = Bits32 (opcode, 7, 0) << 2;
   11057 
   11058                 // d = UInt(Vd:D); n = UInt(Rn);
   11059                 d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22);
   11060                 n = Bits32 (opcode, 19, 16);
   11061 
   11062                 break;
   11063 
   11064             default:
   11065                 return false;
   11066         }
   11067         RegisterInfo base_reg;
   11068         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11069 
   11070         uint32_t Rn = ReadCoreReg (n, &success);
   11071         if (!success)
   11072             return false;
   11073 
   11074         // base = if n == 15 then Align(PC,4) else R[n];
   11075         uint32_t base;
   11076         if (n == 15)
   11077             base = AlignPC (Rn);
   11078         else
   11079             base = Rn;
   11080 
   11081         // address = if add then (base + imm32) else (base - imm32);
   11082         addr_t address;
   11083         if (add)
   11084             address = base + imm32;
   11085         else
   11086             address = base - imm32;
   11087 
   11088         const uint32_t addr_byte_size = GetAddressByteSize();
   11089         uint32_t start_reg = single_reg ? dwarf_s0 : dwarf_d0;
   11090 
   11091         EmulateInstruction::Context context;
   11092         context.type = eContextRegisterLoad;
   11093         context.SetRegisterPlusOffset (base_reg, address - base);
   11094 
   11095         if (single_reg)
   11096         {
   11097             // S[d] = MemA[address,4];
   11098             uint32_t data = MemARead (context, address, addr_byte_size, 0, &success);
   11099             if (!success)
   11100                 return false;
   11101 
   11102             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, start_reg + d, data))
   11103                 return false;
   11104         }
   11105         else
   11106         {
   11107             // word1 = MemA[address,4]; word2 = MemA[address+4,4];
   11108             uint32_t word1 = MemARead (context, address, addr_byte_size, 0, &success);
   11109             if (!success)
   11110                 return false;
   11111 
   11112             context.SetRegisterPlusOffset (base_reg, (address + 4) - base);
   11113             uint32_t word2 = MemARead (context, address + 4, addr_byte_size, 0, &success);
   11114             if (!success)
   11115                 return false;
   11116             // // Combine the word-aligned words in the correct order for current endianness.
   11117             // D[d] = if BigEndian() then word1:word2 else word2:word1;
   11118             uint64_t data64;
   11119             if (GetByteOrder() == eByteOrderBig)
   11120             {
   11121                 data64 = word1;
   11122                 data64 = (data64 << 32) | word2;
   11123             }
   11124             else
   11125             {
   11126                 data64 = word2;
   11127                 data64 = (data64 << 32) | word1;
   11128             }
   11129 
   11130             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, start_reg + d, data64))
   11131                 return false;
   11132         }
   11133     }
   11134     return true;
   11135 }
   11136 
   11137 // A8.6.400 VSTR
   11138 // This instruction stores a signle extension register to memory, using an address from an ARM core register, with an
   11139 // optional offset.
   11140 bool
   11141 EmulateInstructionARM::EmulateVSTR (const uint32_t opcode, ARMEncoding encoding)
   11142 {
   11143 #if 0
   11144     if ConditionPassed() then
   11145         EncodingSpecificOperations(); CheckVFPEnabled(TRUE); NullCheckIfThumbEE(n);
   11146         address = if add then (R[n] + imm32) else (R[n] - imm32);
   11147         if single_reg then
   11148             MemA[address,4] = S[d];
   11149         else
   11150             // Store as two word-aligned words in the correct order for current endianness.
   11151             MemA[address,4] = if BigEndian() then D[d]<63:32> else D[d]<31:0>;
   11152             MemA[address+4,4] = if BigEndian() then D[d]<31:0> else D[d]<63:32>;
   11153 #endif
   11154 
   11155     bool success = false;
   11156 
   11157     if (ConditionPassed (opcode))
   11158     {
   11159         bool single_reg;
   11160         bool add;
   11161         uint32_t imm32;
   11162         uint32_t d;
   11163         uint32_t n;
   11164 
   11165         switch (encoding)
   11166         {
   11167             case eEncodingT1:
   11168             case eEncodingA1:
   11169                 // single_reg = FALSE; add = (U == 1); imm32 = ZeroExtend(imm8:00, 32);
   11170                 single_reg = false;
   11171                 add = BitIsSet (opcode, 23);
   11172                 imm32 = Bits32 (opcode, 7, 0) << 2;
   11173 
   11174                 // d = UInt(D:Vd); n = UInt(Rn);
   11175                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11176                 n = Bits32 (opcode, 19, 16);
   11177 
   11178                 // if n == 15 && CurrentInstrSet() != InstrSet_ARM then UNPREDICTABLE;
   11179                 if ((n == 15) && (CurrentInstrSet() != eModeARM))
   11180                     return false;
   11181 
   11182                 break;
   11183 
   11184             case eEncodingT2:
   11185             case eEncodingA2:
   11186                 // single_reg = TRUE; add = (U == 1); imm32 = ZeroExtend(imm8:00, 32);
   11187                 single_reg = true;
   11188                 add = BitIsSet (opcode, 23);
   11189                 imm32 = Bits32 (opcode, 7, 0) << 2;
   11190 
   11191                 // d = UInt(Vd:D); n = UInt(Rn);
   11192                 d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22);
   11193                 n = Bits32 (opcode, 19, 16);
   11194 
   11195                 // if n == 15 && CurrentInstrSet() != InstrSet_ARM then UNPREDICTABLE;
   11196                 if ((n == 15) && (CurrentInstrSet() != eModeARM))
   11197                     return false;
   11198 
   11199                 break;
   11200 
   11201             default:
   11202                 return false;
   11203         }
   11204 
   11205         RegisterInfo base_reg;
   11206         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11207 
   11208         uint32_t Rn = ReadCoreReg (n, &success);
   11209         if (!success)
   11210             return false;
   11211 
   11212         // address = if add then (R[n] + imm32) else (R[n] - imm32);
   11213         addr_t address;
   11214         if (add)
   11215             address = Rn + imm32;
   11216         else
   11217             address = Rn - imm32;
   11218 
   11219         const uint32_t addr_byte_size = GetAddressByteSize();
   11220         uint32_t start_reg = single_reg ? dwarf_s0 : dwarf_d0;
   11221 
   11222         RegisterInfo data_reg;
   11223         GetRegisterInfo (eRegisterKindDWARF, start_reg + d, data_reg);
   11224         EmulateInstruction::Context context;
   11225         context.type = eContextRegisterStore;
   11226         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   11227 
   11228         if (single_reg)
   11229         {
   11230             // MemA[address,4] = S[d];
   11231             uint32_t data = ReadRegisterUnsigned (eRegisterKindDWARF, start_reg + d, 0, &success);
   11232             if (!success)
   11233                 return false;
   11234 
   11235             if (!MemAWrite (context, address, data, addr_byte_size))
   11236                 return false;
   11237         }
   11238         else
   11239         {
   11240             // // Store as two word-aligned words in the correct order for current endianness.
   11241             // MemA[address,4] = if BigEndian() then D[d]<63:32> else D[d]<31:0>;
   11242             // MemA[address+4,4] = if BigEndian() then D[d]<31:0> else D[d]<63:32>;
   11243             uint64_t data = ReadRegisterUnsigned (eRegisterKindDWARF, start_reg + d, 0, &success);
   11244             if (!success)
   11245                 return false;
   11246 
   11247             if (GetByteOrder() == eByteOrderBig)
   11248             {
   11249                 if (!MemAWrite (context, address, Bits64 (data, 63, 32), addr_byte_size))
   11250                     return false;
   11251 
   11252                 context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, (address + 4) - Rn);
   11253                 if (!MemAWrite (context, address + 4, Bits64 (data, 31, 0), addr_byte_size))
   11254                     return false;
   11255             }
   11256             else
   11257             {
   11258                 if (!MemAWrite (context, address, Bits64 (data, 31, 0), addr_byte_size))
   11259                     return false;
   11260 
   11261                 context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, (address + 4) - Rn);
   11262                 if (!MemAWrite (context, address + 4, Bits64 (data, 63, 32), addr_byte_size))
   11263                     return false;
   11264             }
   11265         }
   11266     }
   11267     return true;
   11268 }
   11269 
   11270 // A8.6.307 VLDI1 (multiple single elements)
   11271 // This instruction loads elements from memory into one, two, three or four registers, without de-interleaving.  Every
   11272 // element of each register is loaded.
   11273 bool
   11274 EmulateInstructionARM::EmulateVLD1Multiple (const uint32_t opcode, ARMEncoding encoding)
   11275 {
   11276 #if 0
   11277     if ConditionPassed() then
   11278         EncodingSpecificOperations(); CheckAdvSIMDEnabled(); NullCheckIfThumbEE(n);
   11279         address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11280         if wback then R[n] = R[n] + (if register_index then R[m] else 8*regs);
   11281         for r = 0 to regs-1
   11282             for e = 0 to elements-1
   11283                 Elem[D[d+r],e,esize] = MemU[address,ebytes];
   11284                 address = address + ebytes;
   11285 #endif
   11286 
   11287     bool success = false;
   11288 
   11289     if (ConditionPassed (opcode))
   11290     {
   11291         uint32_t regs;
   11292         uint32_t alignment;
   11293         uint32_t ebytes;
   11294         uint32_t esize;
   11295         uint32_t elements;
   11296         uint32_t d;
   11297         uint32_t n;
   11298         uint32_t m;
   11299         bool wback;
   11300         bool register_index;
   11301 
   11302         switch (encoding)
   11303         {
   11304             case eEncodingT1:
   11305             case eEncodingA1:
   11306             {
   11307                 // case type of
   11308                     // when 0111
   11309                         // regs = 1; if align<1> == 1 then UNDEFINED;
   11310                     // when 1010
   11311                         // regs = 2; if align == 11 then UNDEFINED;
   11312                     // when 0110
   11313                         // regs = 3; if align<1> == 1 then UNDEFINED;
   11314                     // when 0010
   11315                         // regs = 4;
   11316                     // otherwise
   11317                         // SEE Related encodings;
   11318                 uint32_t type = Bits32 (opcode, 11, 8);
   11319                 uint32_t align = Bits32 (opcode, 5, 4);
   11320                 if (type == 7) // '0111'
   11321                 {
   11322                     regs = 1;
   11323                     if (BitIsSet (align, 1))
   11324                         return false;
   11325                 }
   11326                 else if (type == 10) // '1010'
   11327                 {
   11328                     regs = 2;
   11329                     if (align == 3)
   11330                         return false;
   11331 
   11332                 }
   11333                 else if (type == 6) // '0110'
   11334                 {
   11335                     regs = 3;
   11336                     if (BitIsSet (align, 1))
   11337                         return false;
   11338                 }
   11339                 else if (type == 2) // '0010'
   11340                 {
   11341                     regs = 4;
   11342                 }
   11343                 else
   11344                     return false;
   11345 
   11346                 // alignment = if align == 00 then 1 else 4 << UInt(align);
   11347                 if (align == 0)
   11348                     alignment = 1;
   11349                 else
   11350                     alignment = 4 << align;
   11351 
   11352                 // ebytes = 1 << UInt(size); esize = 8 * ebytes; elements = 8 DIV ebytes;
   11353                 ebytes = 1 << Bits32 (opcode, 7, 6);
   11354                 esize = 8 * ebytes;
   11355                 elements = 8 / ebytes;
   11356 
   11357                 // d = UInt(D:Vd); n = UInt(Rn); m = UInt(Rm);
   11358                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11359                 n = Bits32 (opcode, 19, 15);
   11360                 m = Bits32 (opcode, 3, 0);
   11361 
   11362                 // wback = (m != 15); register_index = (m != 15 && m != 13);
   11363                 wback = (m != 15);
   11364                 register_index = ((m != 15) && (m != 13));
   11365 
   11366                 // if d+regs > 32 then UNPREDICTABLE;
   11367                 if ((d + regs) > 32)
   11368                     return false;
   11369             }
   11370                 break;
   11371 
   11372             default:
   11373                 return false;
   11374         }
   11375 
   11376         RegisterInfo base_reg;
   11377         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11378 
   11379         uint32_t Rn = ReadCoreReg (n, &success);
   11380         if (!success)
   11381             return false;
   11382 
   11383         // address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11384         addr_t address = Rn;
   11385         if ((address % alignment) != 0)
   11386             return false;
   11387 
   11388         EmulateInstruction::Context context;
   11389         // if wback then R[n] = R[n] + (if register_index then R[m] else 8*regs);
   11390         if (wback)
   11391         {
   11392             uint32_t Rm = ReadCoreReg (m, &success);
   11393             if (!success)
   11394                 return false;
   11395 
   11396             uint32_t offset;
   11397             if (register_index)
   11398                 offset = Rm;
   11399             else
   11400                 offset = 8 * regs;
   11401 
   11402             uint32_t value = Rn + offset;
   11403             context.type = eContextAdjustBaseRegister;
   11404             context.SetRegisterPlusOffset (base_reg, offset);
   11405 
   11406             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, value))
   11407                 return false;
   11408 
   11409         }
   11410 
   11411         // for r = 0 to regs-1
   11412         for (uint32_t r = 0; r < regs; ++r)
   11413         {
   11414             // for e = 0 to elements-1
   11415             uint64_t assembled_data = 0;
   11416             for (uint32_t e = 0; e < elements; ++e)
   11417             {
   11418                 // Elem[D[d+r],e,esize] = MemU[address,ebytes];
   11419                 context.type = eContextRegisterLoad;
   11420                 context.SetRegisterPlusOffset (base_reg, address - Rn);
   11421                 uint64_t data = MemURead (context, address, ebytes, 0, &success);
   11422                 if (!success)
   11423                     return false;
   11424 
   11425                 assembled_data = (data << (e * esize)) | assembled_data; // New data goes to the left of existing data
   11426 
   11427                 // address = address + ebytes;
   11428                 address = address + ebytes;
   11429             }
   11430             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_d0 + d + r, assembled_data))
   11431                 return false;
   11432         }
   11433     }
   11434     return true;
   11435 }
   11436 
   11437 // A8.6.308 VLD1 (single element to one lane)
   11438 //
   11439 bool
   11440 EmulateInstructionARM::EmulateVLD1Single (const uint32_t opcode, const ARMEncoding encoding)
   11441 {
   11442 #if 0
   11443     if ConditionPassed() then
   11444         EncodingSpecificOperations(); CheckAdvSIMDEnabled(); NullCheckIfThumbEE(n);
   11445         address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11446         if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   11447         Elem[D[d],index,esize] = MemU[address,ebytes];
   11448 #endif
   11449 
   11450     bool success = false;
   11451 
   11452     if (ConditionPassed (opcode))
   11453     {
   11454         uint32_t ebytes;
   11455         uint32_t esize;
   11456         uint32_t index;
   11457         uint32_t alignment;
   11458         uint32_t d;
   11459         uint32_t n;
   11460         uint32_t m;
   11461         bool wback;
   11462         bool register_index;
   11463 
   11464         switch (encoding)
   11465         {
   11466             case eEncodingT1:
   11467             case eEncodingA1:
   11468             {
   11469                 uint32_t size = Bits32 (opcode, 11, 10);
   11470                 uint32_t index_align = Bits32 (opcode, 7, 4);
   11471                 // if size == 11 then SEE VLD1 (single element to all lanes);
   11472                 if (size == 3)
   11473                    return EmulateVLD1SingleAll (opcode, encoding);
   11474                 // case size of
   11475                 if (size == 0) // when '00'
   11476                 {
   11477                     // if index_align<0> != 0 then UNDEFINED;
   11478                     if (BitIsClear (index_align, 0))
   11479                         return false;
   11480 
   11481                     // ebytes = 1; esize = 8; index = UInt(index_align<3:1>); alignment = 1;
   11482                     ebytes = 1;
   11483                     esize = 8;
   11484                     index = Bits32 (index_align, 3, 1);
   11485                     alignment = 1;
   11486                 }
   11487                 else if (size == 1) // when 01
   11488                 {
   11489                     // if index_align<1> != 0 then UNDEFINED;
   11490                     if (BitIsClear (index_align, 1))
   11491                         return false;
   11492 
   11493                     // ebytes = 2; esize = 16; index = UInt(index_align<3:2>);
   11494                     ebytes = 2;
   11495                     esize = 16;
   11496                     index = Bits32 (index_align, 3, 2);
   11497 
   11498                     // alignment = if index_align<0> == 0 then 1 else 2;
   11499                     if (BitIsClear (index_align, 0))
   11500                         alignment = 1;
   11501                     else
   11502                         alignment = 2;
   11503                 }
   11504                 else if (size == 2) // when 10
   11505                 {
   11506                     // if index_align<2> != 0 then UNDEFINED;
   11507                     if (BitIsClear (index_align, 2))
   11508                         return false;
   11509 
   11510                     // if index_align<1:0> != 00 && index_align<1:0> != 11 then UNDEFINED;
   11511                     if ((Bits32 (index_align, 1, 0) != 0) && (Bits32 (index_align, 1, 0) != 3))
   11512                         return false;
   11513 
   11514                     // ebytes = 4; esize = 32; index = UInt(index_align<3>);
   11515                     ebytes = 4;
   11516                     esize = 32;
   11517                     index = Bit32 (index_align, 3);
   11518 
   11519                     // alignment = if index_align<1:0> == 00 then 1 else 4;
   11520                     if (Bits32 (index_align, 1, 0) == 0)
   11521                         alignment = 1;
   11522                     else
   11523                         alignment = 4;
   11524                 }
   11525                 else
   11526                 {
   11527                     return false;
   11528                 }
   11529                 // d = UInt(D:Vd); n = UInt(Rn); m = UInt(Rm);
   11530                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11531                 n = Bits32 (opcode, 19, 16);
   11532                 m = Bits32 (opcode, 3, 0);
   11533 
   11534                 // wback = (m != 15); register_index = (m != 15 && m != 13); if n == 15 then UNPREDICTABLE;
   11535                 wback = (m != 15);
   11536                 register_index = ((m != 15) && (m != 13));
   11537 
   11538                 if (n == 15)
   11539                     return false;
   11540 
   11541             }
   11542                 break;
   11543 
   11544             default:
   11545                 return false;
   11546         }
   11547 
   11548         RegisterInfo base_reg;
   11549         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11550 
   11551         uint32_t Rn = ReadCoreReg (n, &success);
   11552         if (!success)
   11553             return false;
   11554 
   11555         // address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11556         addr_t address = Rn;
   11557         if ((address % alignment) != 0)
   11558             return false;
   11559 
   11560         EmulateInstruction::Context context;
   11561         // if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   11562         if (wback)
   11563         {
   11564             uint32_t Rm = ReadCoreReg (m, &success);
   11565             if (!success)
   11566                 return false;
   11567 
   11568             uint32_t offset;
   11569             if (register_index)
   11570                 offset = Rm;
   11571             else
   11572                 offset = ebytes;
   11573 
   11574             uint32_t value = Rn + offset;
   11575 
   11576             context.type = eContextAdjustBaseRegister;
   11577             context.SetRegisterPlusOffset (base_reg, offset);
   11578 
   11579             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, value))
   11580                 return false;
   11581         }
   11582 
   11583         // Elem[D[d],index,esize] = MemU[address,ebytes];
   11584         uint32_t element = MemURead (context, address, esize, 0, &success);
   11585         if (!success)
   11586             return false;
   11587 
   11588         element = element << (index * esize);
   11589 
   11590         uint64_t reg_data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_d0 + d, 0, &success);
   11591         if (!success)
   11592             return false;
   11593 
   11594         uint64_t all_ones = -1;
   11595         uint64_t mask = all_ones << ((index+1) * esize);  // mask is all 1's to left of where 'element' goes, & all 0's
   11596                                                           // at element & to the right of element.
   11597         if (index > 0)
   11598             mask = mask | Bits64 (all_ones, (index * esize) - 1, 0); // add 1's to the right of where 'element' goes.
   11599                                                                      // now mask should be 0's where element goes & 1's
   11600                                                                      // everywhere else.
   11601 
   11602         uint64_t masked_reg = reg_data & mask;  // Take original reg value & zero out 'element' bits
   11603         reg_data = masked_reg & element;        // Put 'element' into those bits in reg_data.
   11604 
   11605         context.type = eContextRegisterLoad;
   11606         if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + d, reg_data))
   11607             return false;
   11608     }
   11609     return true;
   11610 }
   11611 
   11612 // A8.6.391 VST1 (multiple single elements)
   11613 // Vector Store (multiple single elements) stores elements to memory from one, two, three, or four regsiters, without
   11614 // interleaving.  Every element of each register is stored.
   11615 bool
   11616 EmulateInstructionARM::EmulateVST1Multiple (const uint32_t opcode, ARMEncoding encoding)
   11617 {
   11618 #if 0
   11619     if ConditionPassed() then
   11620         EncodingSpecificOperations(); CheckAdvSIMDEnabled(); NullCheckIfThumbEE(n);
   11621         address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11622         if wback then R[n] = R[n] + (if register_index then R[m] else 8*regs);
   11623         for r = 0 to regs-1
   11624             for e = 0 to elements-1
   11625                 MemU[address,ebytes] = Elem[D[d+r],e,esize];
   11626                 address = address + ebytes;
   11627 #endif
   11628 
   11629     bool success = false;
   11630 
   11631     if (ConditionPassed (opcode))
   11632     {
   11633         uint32_t regs;
   11634         uint32_t alignment;
   11635         uint32_t ebytes;
   11636         uint32_t esize;
   11637         uint32_t elements;
   11638         uint32_t d;
   11639         uint32_t n;
   11640         uint32_t m;
   11641         bool wback;
   11642         bool register_index;
   11643 
   11644         switch (encoding)
   11645         {
   11646             case eEncodingT1:
   11647             case eEncodingA1:
   11648             {
   11649                 uint32_t type = Bits32 (opcode, 11, 8);
   11650                 uint32_t align = Bits32 (opcode, 5, 4);
   11651 
   11652                 // case type of
   11653                 if (type == 7)    // when 0111
   11654                 {
   11655                     // regs = 1; if align<1> == 1 then UNDEFINED;
   11656                     regs = 1;
   11657                     if (BitIsSet (align, 1))
   11658                         return false;
   11659                 }
   11660                 else if (type == 10) // when 1010
   11661                 {
   11662                     // regs = 2; if align == 11 then UNDEFINED;
   11663                     regs = 2;
   11664                     if (align == 3)
   11665                         return false;
   11666                 }
   11667                 else if (type == 6) // when 0110
   11668                 {
   11669                     // regs = 3; if align<1> == 1 then UNDEFINED;
   11670                     regs = 3;
   11671                     if (BitIsSet (align, 1))
   11672                         return false;
   11673                 }
   11674                 else if (type == 2) // when 0010
   11675                     // regs = 4;
   11676                     regs = 4;
   11677                 else // otherwise
   11678                     // SEE Related encodings;
   11679                     return false;
   11680 
   11681                 // alignment = if align == 00 then 1 else 4 << UInt(align);
   11682                 if (align == 0)
   11683                     alignment = 1;
   11684                 else
   11685                     alignment = 4 << align;
   11686 
   11687                 // ebytes = 1 << UInt(size); esize = 8 * ebytes; elements = 8 DIV ebytes;
   11688                 ebytes = 1 << Bits32 (opcode,7, 6);
   11689                 esize = 8 * ebytes;
   11690                 elements = 8 / ebytes;
   11691 
   11692                 // d = UInt(D:Vd); n = UInt(Rn); m = UInt(Rm);
   11693                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11694                 n = Bits32 (opcode, 19, 16);
   11695                 m = Bits32 (opcode, 3, 0);
   11696 
   11697                 // wback = (m != 15); register_index = (m != 15 && m != 13);
   11698                 wback = (m != 15);
   11699                 register_index = ((m != 15) && (m != 13));
   11700 
   11701                 // if d+regs > 32 then UNPREDICTABLE; if n == 15 then UNPREDICTABLE;
   11702                 if ((d + regs) > 32)
   11703                     return false;
   11704 
   11705                 if (n == 15)
   11706                     return false;
   11707 
   11708             }
   11709                 break;
   11710 
   11711             default:
   11712                 return false;
   11713         }
   11714 
   11715         RegisterInfo base_reg;
   11716         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11717 
   11718         uint32_t Rn = ReadCoreReg (n, &success);
   11719         if (!success)
   11720             return false;
   11721 
   11722         // address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11723         addr_t address = Rn;
   11724         if ((address % alignment) != 0)
   11725             return false;
   11726 
   11727         EmulateInstruction::Context context;
   11728         // if wback then R[n] = R[n] + (if register_index then R[m] else 8*regs);
   11729         if (wback)
   11730         {
   11731             uint32_t Rm = ReadCoreReg (m, &success);
   11732             if (!success)
   11733                 return false;
   11734 
   11735             uint32_t offset;
   11736             if (register_index)
   11737                 offset = Rm;
   11738             else
   11739                 offset = 8 * regs;
   11740 
   11741             context.type = eContextAdjustBaseRegister;
   11742             context.SetRegisterPlusOffset (base_reg, offset);
   11743 
   11744             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, Rn + offset))
   11745                 return false;
   11746         }
   11747 
   11748         RegisterInfo data_reg;
   11749         context.type = eContextRegisterStore;
   11750         // for r = 0 to regs-1
   11751         for (uint32_t r = 0; r < regs; ++r)
   11752         {
   11753             GetRegisterInfo (eRegisterKindDWARF, dwarf_d0 + d + r, data_reg);
   11754             uint64_t register_data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_d0 + d + r, 0, &success);
   11755             if (!success)
   11756                 return false;
   11757 
   11758              // for e = 0 to elements-1
   11759             for (uint32_t e = 0; e < elements; ++e)
   11760             {
   11761                 // MemU[address,ebytes] = Elem[D[d+r],e,esize];
   11762                 uint64_t word = Bits64 (register_data, ((e + 1) * esize) - 1, e * esize);
   11763 
   11764                 context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   11765                 if (!MemUWrite (context, address, word, ebytes))
   11766                     return false;
   11767 
   11768                 // address = address + ebytes;
   11769                 address = address + ebytes;
   11770             }
   11771         }
   11772     }
   11773     return true;
   11774 }
   11775 
   11776 // A8.6.392 VST1 (single element from one lane)
   11777 // This instruction stores one element to memory from one element of a register.
   11778 bool
   11779 EmulateInstructionARM::EmulateVST1Single (const uint32_t opcode, ARMEncoding encoding)
   11780 {
   11781 #if 0
   11782     if ConditionPassed() then
   11783         EncodingSpecificOperations(); CheckAdvSIMDEnabled(); NullCheckIfThumbEE(n);
   11784         address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11785         if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   11786         MemU[address,ebytes] = Elem[D[d],index,esize];
   11787 #endif
   11788 
   11789     bool success = false;
   11790 
   11791     if (ConditionPassed (opcode))
   11792     {
   11793         uint32_t ebytes;
   11794         uint32_t esize;
   11795         uint32_t index;
   11796         uint32_t alignment;
   11797         uint32_t d;
   11798         uint32_t n;
   11799         uint32_t m;
   11800         bool wback;
   11801         bool register_index;
   11802 
   11803         switch (encoding)
   11804         {
   11805             case eEncodingT1:
   11806             case eEncodingA1:
   11807             {
   11808                 uint32_t size = Bits32 (opcode, 11, 10);
   11809                 uint32_t index_align = Bits32 (opcode, 7, 4);
   11810 
   11811                 // if size == 11 then UNDEFINED;
   11812                 if (size == 3)
   11813                     return false;
   11814 
   11815                 // case size of
   11816                 if (size == 0) // when 00
   11817                 {
   11818                     // if index_align<0> != 0 then UNDEFINED;
   11819                     if (BitIsClear (index_align, 0))
   11820                         return false;
   11821                     // ebytes = 1; esize = 8; index = UInt(index_align<3:1>); alignment = 1;
   11822                     ebytes = 1;
   11823                     esize = 8;
   11824                     index = Bits32 (index_align, 3, 1);
   11825                     alignment = 1;
   11826                 }
   11827                 else if (size == 1) // when 01
   11828                 {
   11829                     // if index_align<1> != 0 then UNDEFINED;
   11830                     if (BitIsClear (index_align, 1))
   11831                         return false;
   11832 
   11833                     // ebytes = 2; esize = 16; index = UInt(index_align<3:2>);
   11834                     ebytes = 2;
   11835                     esize = 16;
   11836                     index = Bits32 (index_align, 3, 2);
   11837 
   11838                     // alignment = if index_align<0> == 0 then 1 else 2;
   11839                     if (BitIsClear (index_align, 0))
   11840                         alignment = 1;
   11841                     else
   11842                         alignment = 2;
   11843                 }
   11844                 else if (size == 2) // when 10
   11845                 {
   11846                     // if index_align<2> != 0 then UNDEFINED;
   11847                     if (BitIsClear (index_align, 2))
   11848                         return false;
   11849 
   11850                     // if index_align<1:0> != 00 && index_align<1:0> != 11 then UNDEFINED;
   11851                     if ((Bits32 (index_align, 1, 0) != 0) && (Bits32 (index_align, 1, 0) != 3))
   11852                         return false;
   11853 
   11854                     // ebytes = 4; esize = 32; index = UInt(index_align<3>);
   11855                     ebytes = 4;
   11856                     esize = 32;
   11857                     index = Bit32 (index_align, 3);
   11858 
   11859                     // alignment = if index_align<1:0> == 00 then 1 else 4;
   11860                     if (Bits32 (index_align, 1, 0) == 0)
   11861                         alignment = 1;
   11862                     else
   11863                         alignment = 4;
   11864                 }
   11865                 else
   11866                 {
   11867                     return false;
   11868                 }
   11869                 // d = UInt(D:Vd); n = UInt(Rn); m = UInt(Rm);
   11870                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11871                 n = Bits32 (opcode, 19, 16);
   11872                 m = Bits32 (opcode, 3, 0);
   11873 
   11874                 // wback = (m != 15); register_index = (m != 15 && m != 13);  if n == 15 then UNPREDICTABLE;
   11875                 wback = (m != 15);
   11876                 register_index = ((m != 15) && (m != 13));
   11877 
   11878                 if (n == 15)
   11879                     return false;
   11880             }
   11881                 break;
   11882 
   11883             default:
   11884                 return false;
   11885         }
   11886 
   11887         RegisterInfo base_reg;
   11888         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   11889 
   11890         uint32_t Rn = ReadCoreReg (n, &success);
   11891         if (!success)
   11892             return false;
   11893 
   11894         // address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11895         addr_t address = Rn;
   11896         if ((address % alignment) != 0)
   11897             return false;
   11898 
   11899         EmulateInstruction::Context context;
   11900         // if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   11901         if (wback)
   11902         {
   11903             uint32_t Rm = ReadCoreReg (m, &success);
   11904             if (!success)
   11905                 return false;
   11906 
   11907             uint32_t offset;
   11908             if (register_index)
   11909                 offset = Rm;
   11910             else
   11911                 offset = ebytes;
   11912 
   11913             context.type = eContextAdjustBaseRegister;
   11914             context.SetRegisterPlusOffset (base_reg, offset);
   11915 
   11916             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, Rn + offset))
   11917                 return false;
   11918         }
   11919 
   11920         // MemU[address,ebytes] = Elem[D[d],index,esize];
   11921         uint64_t register_data = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_d0 + d, 0, &success);
   11922         if (!success)
   11923             return false;
   11924 
   11925         uint64_t word = Bits64 (register_data, ((index + 1) * esize) - 1,  index * esize);
   11926 
   11927         RegisterInfo data_reg;
   11928         GetRegisterInfo (eRegisterKindDWARF, dwarf_d0 + d, data_reg);
   11929         context.type = eContextRegisterStore;
   11930         context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn);
   11931 
   11932         if (!MemUWrite (context, address, word, ebytes))
   11933             return false;
   11934     }
   11935     return true;
   11936 }
   11937 
   11938 // A8.6.309 VLD1 (single element to all lanes)
   11939 // This instruction loads one element from memory into every element of one or two vectors.
   11940 bool
   11941 EmulateInstructionARM::EmulateVLD1SingleAll (const uint32_t opcode, const ARMEncoding encoding)
   11942 {
   11943 #if 0
   11944     if ConditionPassed() then
   11945         EncodingSpecificOperations(); CheckAdvSIMDEnabled(); NullCheckIfThumbEE(n);
   11946         address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   11947         if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   11948         replicated_element = Replicate(MemU[address,ebytes], elements);
   11949         for r = 0 to regs-1
   11950             D[d+r] = replicated_element;
   11951 #endif
   11952 
   11953     bool success = false;
   11954 
   11955     if (ConditionPassed (opcode))
   11956     {
   11957         uint32_t ebytes;
   11958         uint32_t elements;
   11959         uint32_t regs;
   11960         uint32_t alignment;
   11961         uint32_t d;
   11962         uint32_t n;
   11963         uint32_t m;
   11964         bool wback;
   11965         bool register_index;
   11966 
   11967         switch (encoding)
   11968         {
   11969             case eEncodingT1:
   11970             case eEncodingA1:
   11971             {
   11972                 //if size == 11 || (size == 00 && a == 1) then UNDEFINED;
   11973                 uint32_t size = Bits32 (opcode, 7, 6);
   11974                 if ((size == 3) || ((size == 0) && BitIsSet (opcode, 4)))
   11975                     return false;
   11976 
   11977                 //ebytes = 1 << UInt(size); elements = 8 DIV ebytes; regs = if T == 0 then 1 else 2;
   11978                 ebytes = 1 << size;
   11979                 elements = 8 / ebytes;
   11980                 if (BitIsClear (opcode, 5))
   11981                     regs = 1;
   11982                 else
   11983                     regs = 2;
   11984 
   11985                 //alignment = if a == 0 then 1 else ebytes;
   11986                 if (BitIsClear (opcode, 4))
   11987                     alignment = 1;
   11988                 else
   11989                     alignment = ebytes;
   11990 
   11991                 //d = UInt(D:Vd); n = UInt(Rn); m = UInt(Rm);
   11992                 d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12);
   11993                 n = Bits32 (opcode, 19, 16);
   11994                 m = Bits32 (opcode, 3, 0);
   11995 
   11996                 //wback = (m != 15); register_index = (m != 15 && m != 13);
   11997                 wback = (m != 15);
   11998                 register_index = ((m != 15) && (m != 13));
   11999 
   12000                 //if d+regs > 32 then UNPREDICTABLE; if n == 15 then UNPREDICTABLE;
   12001                 if ((d + regs) > 32)
   12002                     return false;
   12003 
   12004                 if (n == 15)
   12005                     return false;
   12006             }
   12007             break;
   12008 
   12009             default:
   12010                 return false;
   12011         }
   12012 
   12013         RegisterInfo base_reg;
   12014         GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg);
   12015 
   12016         uint32_t Rn = ReadCoreReg (n, &success);
   12017         if (!success)
   12018             return false;
   12019 
   12020         // address = R[n]; if (address MOD alignment) != 0 then GenerateAlignmentException();
   12021         addr_t address = Rn;
   12022         if ((address % alignment) != 0)
   12023             return false;
   12024 
   12025         EmulateInstruction::Context context;
   12026         // if wback then R[n] = R[n] + (if register_index then R[m] else ebytes);
   12027         if (wback)
   12028         {
   12029             uint32_t Rm = ReadCoreReg (m, &success);
   12030             if (!success)
   12031                 return false;
   12032 
   12033             uint32_t offset;
   12034             if (register_index)
   12035                 offset = Rm;
   12036             else
   12037                 offset = ebytes;
   12038 
   12039             context.type = eContextAdjustBaseRegister;
   12040             context.SetRegisterPlusOffset (base_reg, offset);
   12041 
   12042             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, Rn + offset))
   12043                 return false;
   12044         }
   12045 
   12046         // replicated_element = Replicate(MemU[address,ebytes], elements);
   12047 
   12048         context.type = eContextRegisterLoad;
   12049         uint64_t word = MemURead (context, address, ebytes, 0, &success);
   12050         if (!success)
   12051             return false;
   12052 
   12053         uint64_t replicated_element = 0;
   12054         uint32_t esize = ebytes * 8;
   12055         for (uint32_t e = 0; e < elements; ++e)
   12056             replicated_element = (replicated_element << esize) | Bits64 (word, esize - 1, 0);
   12057 
   12058         // for r = 0 to regs-1
   12059         for (uint32_t r = 0; r < regs; ++r)
   12060         {
   12061             // D[d+r] = replicated_element;
   12062             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_d0 + d + r, replicated_element))
   12063                 return false;
   12064         }
   12065     }
   12066     return true;
   12067 }
   12068 
   12069 // B6.2.13 SUBS PC, LR and related instructions
   12070 //The SUBS PC, LR, #<const? instruction provides an exception return without the use of the stack.  It subtracts the
   12071 // immediate constant from the LR, branches to the resulting address, and also copies the SPSR to the CPSR.
   12072 bool
   12073 EmulateInstructionARM::EmulateSUBSPcLrEtc (const uint32_t opcode, const ARMEncoding encoding)
   12074 {
   12075 #if 0
   12076     if ConditionPassed() then
   12077         EncodingSpecificOperations();
   12078         if CurrentInstrSet() == InstrSet_ThumbEE then
   12079             UNPREDICTABLE;
   12080         operand2 = if register_form then Shift(R[m], shift_t, shift_n, APSR.C) else imm32;
   12081         case opcode of
   12082             when 0000 result = R[n] AND operand2; // AND
   12083             when 0001 result = R[n] EOR operand2; // EOR
   12084             when 0010 (result, -, -) = AddWithCarry(R[n], NOT(operand2), 1); // SUB
   12085             when 0011 (result, -, -) = AddWithCarry(NOT(R[n]), operand2, 1); // RSB
   12086             when 0100 (result, -, -) = AddWithCarry(R[n], operand2, 0); // ADD
   12087             when 0101 (result, -, -) = AddWithCarry(R[n], operand2, APSR.c); // ADC
   12088             when 0110 (result, -, -) = AddWithCarry(R[n], NOT(operand2), APSR.C); // SBC
   12089             when 0111 (result, -, -) = AddWithCarry(NOT(R[n]), operand2, APSR.C); // RSC
   12090             when 1100 result = R[n] OR operand2; // ORR
   12091             when 1101 result = operand2; // MOV
   12092             when 1110 result = R[n] AND NOT(operand2); // BIC
   12093             when 1111 result = NOT(operand2); // MVN
   12094         CPSRWriteByInstr(SPSR[], 1111, TRUE);
   12095         BranchWritePC(result);
   12096 #endif
   12097 
   12098     bool success = false;
   12099 
   12100     if (ConditionPassed (opcode))
   12101     {
   12102         uint32_t n;
   12103         uint32_t m;
   12104         uint32_t imm32;
   12105         bool register_form;
   12106         ARM_ShifterType shift_t;
   12107         uint32_t shift_n;
   12108         uint32_t code;
   12109 
   12110         switch (encoding)
   12111         {
   12112             case eEncodingT1:
   12113                 // if CurrentInstrSet() == InstrSet_ThumbEE then UNPREDICTABLE
   12114                 // n = 14; imm32 = ZeroExtend(imm8, 32); register_form = FALSE; opcode = 0010; // = SUB
   12115                 n = 14;
   12116                 imm32 = Bits32 (opcode, 7, 0);
   12117                 register_form = false;
   12118                 code = 2;
   12119 
   12120                 // if InITBlock() && !LastInITBlock() then UNPREDICTABLE;
   12121                 if (InITBlock() && !LastInITBlock())
   12122                     return false;
   12123 
   12124                 break;
   12125 
   12126             case eEncodingA1:
   12127                 // n = UInt(Rn); imm32 = ARMExpandImm(imm12); register_form = FALSE;
   12128                 n = Bits32 (opcode, 19, 16);
   12129                 imm32 = ARMExpandImm (opcode);
   12130                 register_form = false;
   12131                 code = Bits32 (opcode, 24, 21);
   12132 
   12133                 break;
   12134 
   12135             case eEncodingA2:
   12136                 // n = UInt(Rn); m = UInt(Rm); register_form = TRUE;
   12137                 n = Bits32 (opcode, 19, 16);
   12138                 m = Bits32 (opcode, 3, 0);
   12139                 register_form = true;
   12140 
   12141                 // (shift_t, shift_n) = DecodeImmShift(type, imm5);
   12142                 shift_n = DecodeImmShiftARM (opcode, shift_t);
   12143 
   12144                 break;
   12145 
   12146             default:
   12147                 return false;
   12148         }
   12149 
   12150         // operand2 = if register_form then Shift(R[m], shift_t, shift_n, APSR.C) else imm32;
   12151         uint32_t operand2;
   12152         if (register_form)
   12153         {
   12154             uint32_t Rm = ReadCoreReg (m, &success);
   12155             if (!success)
   12156                 return false;
   12157 
   12158             operand2 = Shift (Rm, shift_t, shift_n, APSR_C, &success);
   12159             if (!success)
   12160                 return false;
   12161         }
   12162         else
   12163         {
   12164             operand2 = imm32;
   12165         }
   12166 
   12167         uint32_t Rn = ReadCoreReg (n, &success);
   12168         if (!success)
   12169             return false;
   12170 
   12171         AddWithCarryResult result;
   12172 
   12173         // case opcode of
   12174         switch (code)
   12175         {
   12176             case 0: // when 0000
   12177                 // result = R[n] AND operand2; // AND
   12178                 result.result = Rn & operand2;
   12179                 break;
   12180 
   12181             case 1: // when 0001
   12182                 // result = R[n] EOR operand2; // EOR
   12183                 result.result = Rn ^ operand2;
   12184                 break;
   12185 
   12186             case 2: // when 0010
   12187                 // (result, -, -) = AddWithCarry(R[n], NOT(operand2), 1); // SUB
   12188                 result = AddWithCarry (Rn, ~(operand2), 1);
   12189                 break;
   12190 
   12191             case 3: // when 0011
   12192                 // (result, -, -) = AddWithCarry(NOT(R[n]), operand2, 1); // RSB
   12193                 result = AddWithCarry (~(Rn), operand2, 1);
   12194                 break;
   12195 
   12196             case 4: // when 0100
   12197                 // (result, -, -) = AddWithCarry(R[n], operand2, 0); // ADD
   12198                 result = AddWithCarry (Rn, operand2, 0);
   12199                 break;
   12200 
   12201             case 5: // when 0101
   12202                 // (result, -, -) = AddWithCarry(R[n], operand2, APSR.c); // ADC
   12203                 result = AddWithCarry (Rn, operand2, APSR_C);
   12204                 break;
   12205 
   12206             case 6: // when 0110
   12207                 // (result, -, -) = AddWithCarry(R[n], NOT(operand2), APSR.C); // SBC
   12208                 result = AddWithCarry (Rn, ~(operand2), APSR_C);
   12209                 break;
   12210 
   12211             case 7: // when 0111
   12212                 // (result, -, -) = AddWithCarry(NOT(R[n]), operand2, APSR.C); // RSC
   12213                 result = AddWithCarry (~(Rn), operand2, APSR_C);
   12214                 break;
   12215 
   12216             case 10: // when 1100
   12217                 // result = R[n] OR operand2; // ORR
   12218                 result.result = Rn | operand2;
   12219                 break;
   12220 
   12221             case 11: // when 1101
   12222                 // result = operand2; // MOV
   12223                 result.result = operand2;
   12224                 break;
   12225 
   12226             case 12: // when 1110
   12227                 // result = R[n] AND NOT(operand2); // BIC
   12228                 result.result = Rn & ~(operand2);
   12229                 break;
   12230 
   12231             case 15: // when 1111
   12232                 // result = NOT(operand2); // MVN
   12233                 result.result = ~(operand2);
   12234                 break;
   12235 
   12236             default:
   12237                 return false;
   12238         }
   12239         // CPSRWriteByInstr(SPSR[], 1111, TRUE);
   12240 
   12241         // For now, in emulation mode, we don't have access to the SPSR, so we will use the CPSR instead, and hope for
   12242         // the best.
   12243         uint32_t spsr = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_cpsr, 0, &success);
   12244         if (!success)
   12245             return false;
   12246 
   12247         CPSRWriteByInstr (spsr, 15, true);
   12248 
   12249         // BranchWritePC(result);
   12250         EmulateInstruction::Context context;
   12251         context.type = eContextAdjustPC;
   12252         context.SetImmediate (result.result);
   12253 
   12254         BranchWritePC (context, result.result);
   12255     }
   12256     return true;
   12257 }
   12258 
   12259 EmulateInstructionARM::ARMOpcode*
   12260 EmulateInstructionARM::GetARMOpcodeForInstruction (const uint32_t opcode, uint32_t arm_isa)
   12261 {
   12262     static ARMOpcode
   12263     g_arm_opcodes[] =
   12264     {
   12265         //----------------------------------------------------------------------
   12266         // Prologue instructions
   12267         //----------------------------------------------------------------------
   12268 
   12269         // push register(s)
   12270         { 0x0fff0000, 0x092d0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulatePUSH, "push <registers>" },
   12271         { 0x0fff0fff, 0x052d0004, ARMvAll,       eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulatePUSH, "push <register>" },
   12272 
   12273         // set r7 to point to a stack offset
   12274         { 0x0ffff000, 0x028d7000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDRdSPImm, "add r7, sp, #<const>" },
   12275         { 0x0ffff000, 0x024c7000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBR7IPImm, "sub r7, ip, #<const>"},
   12276         // copy the stack pointer to ip
   12277         { 0x0fffffff, 0x01a0c00d, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdSP, "mov ip, sp" },
   12278         { 0x0ffff000, 0x028dc000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDRdSPImm, "add ip, sp, #<const>" },
   12279         { 0x0ffff000, 0x024dc000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBIPSPImm, "sub ip, sp, #<const>"},
   12280 
   12281         // adjust the stack pointer
   12282         { 0x0ffff000, 0x024dd000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "sub sp, sp, #<const>"},
   12283         { 0x0fef0010, 0x004d0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPReg, "sub{s}<c> <Rd>, sp, <Rm>{,<shift>}" },
   12284 
   12285         // push one register
   12286         // if Rn == '1101' && imm12 == '000000000100' then SEE PUSH;
   12287         { 0x0e5f0000, 0x040d0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRRtSP, "str Rt, [sp, #-imm12]!" },
   12288 
   12289         // vector push consecutive extension register(s)
   12290         { 0x0fbf0f00, 0x0d2d0b00, ARMV6T2_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPUSH, "vpush.64 <list>"},
   12291         { 0x0fbf0f00, 0x0d2d0a00, ARMV6T2_ABOVE, eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPUSH, "vpush.32 <list>"},
   12292 
   12293         //----------------------------------------------------------------------
   12294         // Epilogue instructions
   12295         //----------------------------------------------------------------------
   12296 
   12297         { 0x0fff0000, 0x08bd0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulatePOP, "pop <registers>"},
   12298         { 0x0fff0fff, 0x049d0004, ARMvAll,       eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulatePOP, "pop <register>"},
   12299         { 0x0fbf0f00, 0x0cbd0b00, ARMV6T2_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPOP, "vpop.64 <list>"},
   12300         { 0x0fbf0f00, 0x0cbd0a00, ARMV6T2_ABOVE, eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPOP, "vpop.32 <list>"},
   12301 
   12302         //----------------------------------------------------------------------
   12303         // Supervisor Call (previously Software Interrupt)
   12304         //----------------------------------------------------------------------
   12305         { 0x0f000000, 0x0f000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSVC, "svc #imm24"},
   12306 
   12307         //----------------------------------------------------------------------
   12308         // Branch instructions
   12309         //----------------------------------------------------------------------
   12310         { 0x0f000000, 0x0a000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateB, "b #imm24"},
   12311         // To resolve ambiguity, "blx <label>" should come before "bl <label>".
   12312         { 0xfe000000, 0xfa000000, ARMV5_ABOVE,   eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateBLXImmediate, "blx <label>"},
   12313         { 0x0f000000, 0x0b000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBLXImmediate, "bl <label>"},
   12314         { 0x0ffffff0, 0x012fff30, ARMV5_ABOVE,   eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBLXRm, "blx <Rm>"},
   12315         // for example, "bx lr"
   12316         { 0x0ffffff0, 0x012fff10, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBXRm, "bx <Rm>"},
   12317         // bxj
   12318         { 0x0ffffff0, 0x012fff20, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBXJRm, "bxj <Rm>"},
   12319 
   12320         //----------------------------------------------------------------------
   12321         // Data-processing instructions
   12322         //----------------------------------------------------------------------
   12323         // adc (immediate)
   12324         { 0x0fe00000, 0x02a00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADCImm, "adc{s}<c> <Rd>, <Rn>, #const"},
   12325         // adc (register)
   12326         { 0x0fe00010, 0x00a00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADCReg, "adc{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12327         // add (immediate)
   12328         { 0x0fe00000, 0x02800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDImmARM, "add{s}<c> <Rd>, <Rn>, #const"},
   12329         // add (register)
   12330         { 0x0fe00010, 0x00800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDReg, "add{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12331         // add (register-shifted register)
   12332         { 0x0fe00090, 0x00800010, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDRegShift, "add{s}<c> <Rd>, <Rn>, <Rm>, <type> <RS>"},
   12333         // adr
   12334         { 0x0fff0000, 0x028f0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADR, "add<c> <Rd>, PC, #<const>"},
   12335         { 0x0fff0000, 0x024f0000, ARMvAll,       eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateADR, "sub<c> <Rd>, PC, #<const>"},
   12336         // and (immediate)
   12337         { 0x0fe00000, 0x02000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateANDImm, "and{s}<c> <Rd>, <Rn>, #const"},
   12338         // and (register)
   12339         { 0x0fe00010, 0x00000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateANDReg, "and{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12340         // bic (immediate)
   12341         { 0x0fe00000, 0x03c00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBICImm, "bic{s}<c> <Rd>, <Rn>, #const"},
   12342         // bic (register)
   12343         { 0x0fe00010, 0x01c00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBICReg, "bic{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12344         // eor (immediate)
   12345         { 0x0fe00000, 0x02200000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateEORImm, "eor{s}<c> <Rd>, <Rn>, #const"},
   12346         // eor (register)
   12347         { 0x0fe00010, 0x00200000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateEORReg, "eor{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12348         // orr (immediate)
   12349         { 0x0fe00000, 0x03800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateORRImm, "orr{s}<c> <Rd>, <Rn>, #const"},
   12350         // orr (register)
   12351         { 0x0fe00010, 0x01800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateORRReg, "orr{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12352         // rsb (immediate)
   12353         { 0x0fe00000, 0x02600000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSBImm, "rsb{s}<c> <Rd>, <Rn>, #<const>"},
   12354         // rsb (register)
   12355         { 0x0fe00010, 0x00600000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSBReg, "rsb{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12356         // rsc (immediate)
   12357         { 0x0fe00000, 0x02e00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSCImm, "rsc{s}<c> <Rd>, <Rn>, #<const>"},
   12358         // rsc (register)
   12359         { 0x0fe00010, 0x00e00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSCReg, "rsc{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12360         // sbc (immediate)
   12361         { 0x0fe00000, 0x02c00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSBCImm, "sbc{s}<c> <Rd>, <Rn>, #<const>"},
   12362         // sbc (register)
   12363         { 0x0fe00010, 0x00c00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSBCReg, "sbc{s}<c> <Rd>, <Rn>, <Rm> {,<shift>}"},
   12364         // sub (immediate, ARM)
   12365         { 0x0fe00000, 0x02400000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBImmARM, "sub{s}<c> <Rd>, <Rn>, #<const>"},
   12366         // sub (sp minus immediate)
   12367         { 0x0fef0000, 0x024d0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "sub{s}<c> <Rd>, sp, #<const>"},
   12368         // sub (register)
   12369         { 0x0fe00010, 0x00400000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBReg, "sub{s}<c> <Rd>, <Rn>, <Rm>{,<shift>}"},
   12370         // teq (immediate)
   12371         { 0x0ff0f000, 0x03300000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTEQImm, "teq<c> <Rn>, #const"},
   12372         // teq (register)
   12373         { 0x0ff0f010, 0x01300000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTEQReg, "teq<c> <Rn>, <Rm> {,<shift>}"},
   12374         // tst (immediate)
   12375         { 0x0ff0f000, 0x03100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTSTImm, "tst<c> <Rn>, #const"},
   12376         // tst (register)
   12377         { 0x0ff0f010, 0x01100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTSTReg, "tst<c> <Rn>, <Rm> {,<shift>}"},
   12378 
   12379         // mov (immediate)
   12380         { 0x0fef0000, 0x03a00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdImm, "mov{s}<c> <Rd>, #<const>"},
   12381         { 0x0ff00000, 0x03000000, ARMV6T2_ABOVE, eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdImm, "movw<c> <Rd>, #<imm16>" },
   12382         // mov (register)
   12383         { 0x0fef0ff0, 0x01a00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdRm, "mov{s}<c> <Rd>, <Rm>"},
   12384         // mvn (immediate)
   12385         { 0x0fef0000, 0x03e00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMVNImm, "mvn{s}<c> <Rd>, #<const>"},
   12386         // mvn (register)
   12387         { 0x0fef0010, 0x01e00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMVNReg, "mvn{s}<c> <Rd>, <Rm> {,<shift>}"},
   12388         // cmn (immediate)
   12389         { 0x0ff0f000, 0x03700000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMNImm, "cmn<c> <Rn>, #<const>"},
   12390         // cmn (register)
   12391         { 0x0ff0f010, 0x01700000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMNReg, "cmn<c> <Rn>, <Rm> {,<shift>}"},
   12392         // cmp (immediate)
   12393         { 0x0ff0f000, 0x03500000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMPImm, "cmp<c> <Rn>, #<const>"},
   12394         // cmp (register)
   12395         { 0x0ff0f010, 0x01500000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMPReg, "cmp<c> <Rn>, <Rm> {,<shift>}"},
   12396         // asr (immediate)
   12397         { 0x0fef0070, 0x01a00040, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateASRImm, "asr{s}<c> <Rd>, <Rm>, #imm"},
   12398         // asr (register)
   12399         { 0x0fef00f0, 0x01a00050, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateASRReg, "asr{s}<c> <Rd>, <Rn>, <Rm>"},
   12400         // lsl (immediate)
   12401         { 0x0fef0070, 0x01a00000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSLImm, "lsl{s}<c> <Rd>, <Rm>, #imm"},
   12402         // lsl (register)
   12403         { 0x0fef00f0, 0x01a00010, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSLReg, "lsl{s}<c> <Rd>, <Rn>, <Rm>"},
   12404         // lsr (immediate)
   12405         { 0x0fef0070, 0x01a00020, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSRImm, "lsr{s}<c> <Rd>, <Rm>, #imm"},
   12406         // lsr (register)
   12407         { 0x0fef00f0, 0x01a00050, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSRReg, "lsr{s}<c> <Rd>, <Rn>, <Rm>"},
   12408         // rrx is a special case encoding of ror (immediate)
   12409         { 0x0fef0ff0, 0x01a00060, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRRX, "rrx{s}<c> <Rd>, <Rm>"},
   12410         // ror (immediate)
   12411         { 0x0fef0070, 0x01a00060, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRORImm, "ror{s}<c> <Rd>, <Rm>, #imm"},
   12412         // ror (register)
   12413         { 0x0fef00f0, 0x01a00070, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRORReg, "ror{s}<c> <Rd>, <Rn>, <Rm>"},
   12414         // mul
   12415         { 0x0fe000f0, 0x00000090, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMUL, "mul{s}<c> <Rd>,<R>,<Rm>" },
   12416 
   12417         // subs pc, lr and related instructions
   12418         { 0x0e10f000, 0x0210f000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPcLrEtc, "<opc>S<c> PC,#<const> | <Rn>,#<const>" },
   12419         { 0x0e10f010, 0x0010f000, ARMvAll,       eEncodingA2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPcLrEtc, "<opc>S<c> PC,<Rn>,<Rm{,<shift>}" },
   12420 
   12421         //----------------------------------------------------------------------
   12422         // Load instructions
   12423         //----------------------------------------------------------------------
   12424         { 0x0fd00000, 0x08900000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDM, "ldm<c> <Rn>{!} <registers>" },
   12425         { 0x0fd00000, 0x08100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDMDA, "ldmda<c> <Rn>{!} <registers>" },
   12426         { 0x0fd00000, 0x09100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDMDB, "ldmdb<c> <Rn>{!} <registers>" },
   12427         { 0x0fd00000, 0x09900000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDMIB, "ldmib<c> <Rn<{!} <registers>" },
   12428         { 0x0e500000, 0x04100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRImmediateARM, "ldr<c> <Rt> [<Rn> {#+/-<imm12>}]" },
   12429         { 0x0e500010, 0x06100000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRRegister, "ldr<c> <Rt> [<Rn> +/-<Rm> {<shift>}] {!}" },
   12430         { 0x0e5f0000, 0x045f0000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBLiteral, "ldrb<c> <Rt>, [...]"},
   12431         { 0xfe500010, 0x06500000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBRegister, "ldrb<c> <Rt>, [<Rn>,+/-<Rm>{, <shift>}]{!}" },
   12432         { 0x0e5f00f0, 0x005f00b0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHLiteral, "ldrh<c> <Rt>, <label>" },
   12433         { 0x0e5000f0, 0x001000b0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHRegister, "ldrh<c> <Rt>,[<Rn>,+/-<Rm>]{!}"  },
   12434         { 0x0e5000f0, 0x005000d0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBImmediate, "ldrsb<c> <Rt>, [<Rn>{,#+/-<imm8>}]" },
   12435         { 0x0e5f00f0, 0x005f00d0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBLiteral, "ldrsb<c> <Rt> <label>" },
   12436         { 0x0e5000f0, 0x001000d0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBRegister, "ldrsb<c> <Rt>,[<Rn>,+/-<Rm>]{!}" },
   12437         { 0x0e5000f0, 0x005000f0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHImmediate, "ldrsh<c> <Rt>,[<Rn>{,#+/-<imm8>}]"},
   12438         { 0x0e5f00f0, 0x005f00f0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHLiteral, "ldrsh<c> <Rt>,<label>" },
   12439         { 0x0e5000f0, 0x001000f0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHRegister, "ldrsh<c> <Rt>,[<Rn>,+/-<Rm>]{!}" },
   12440         { 0x0e5000f0, 0x004000d0, ARMV5TE_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRDImmediate, "ldrd<c> <Rt>, <Rt2>, [<Rn>,#+/-<imm8>]!"},
   12441         { 0x0e500ff0, 0x000000d0, ARMV5TE_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRDRegister, "ldrd<c> <Rt>, <Rt2>, [<Rn>, +/-<Rm>]{!}"},
   12442         { 0x0e100f00, 0x0c100b00, ARMvAll,       eEncodingA1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVLDM, "vldm{mode}<c> <Rn>{!}, <list>"},
   12443         { 0x0e100f00, 0x0c100a00, ARMvAll,       eEncodingA2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVLDM, "vldm{mode}<c> <Rn>{!}, <list>"},
   12444         { 0x0f300f00, 0x0d100b00, ARMvAll,       eEncodingA1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVLDR, "vldr<c> <Dd>, [<Rn>{,#+/-<imm>}]"},
   12445         { 0x0f300f00, 0x0d100a00, ARMvAll,       eEncodingA2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVLDR, "vldr<c> <Sd>, [<Rn>{,#+/-<imm>}]"},
   12446         { 0xffb00000, 0xf4200000, ARMvAll,       eEncodingA1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1Multiple, "vld1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12447         { 0xffb00300, 0xf4a00000, ARMvAll,       eEncodingA1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1Single, "vld1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12448         { 0xffb00f00, 0xf4a00c00, ARMvAll,       eEncodingA1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1SingleAll, "vld1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12449 
   12450         //----------------------------------------------------------------------
   12451         // Store instructions
   12452         //----------------------------------------------------------------------
   12453         { 0x0fd00000, 0x08800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTM, "stm<c> <Rn>{!} <registers>" },
   12454         { 0x0fd00000, 0x08000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTMDA, "stmda<c> <Rn>{!} <registers>" },
   12455         { 0x0fd00000, 0x09000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTMDB, "stmdb<c> <Rn>{!} <registers>" },
   12456         { 0x0fd00000, 0x09800000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTMIB, "stmib<c> <Rn>{!} <registers>" },
   12457         { 0x0e500010, 0x06000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRRegister, "str<c> <Rt> [<Rn> +/-<Rm> {<shift>}]{!}" },
   12458         { 0x0e5000f0, 0x000000b0, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRHRegister, "strh<c> <Rt>,[<Rn>,+/-<Rm>[{!}" },
   12459         { 0x0ff00ff0, 0x01800f90, ARMV6_ABOVE,   eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTREX, "strex<c> <Rd>, <Rt>, [<Rn>]"},
   12460         { 0x0e500000, 0x04400000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRBImmARM, "strb<c> <Rt>,[<Rn>,#+/-<imm12>]!"},
   12461         { 0x0e500000, 0x04000000, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRImmARM, "str<c> <Rt>,[<Rn>,#+/-<imm12>]!"},
   12462         { 0x0e5000f0, 0x004000f0, ARMV5TE_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRDImm, "strd<c> <Rt>, <Rt2>, [<Rn> #+/-<imm8>]!"},
   12463         { 0x0e500ff0, 0x000000f0, ARMV5TE_ABOVE, eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRDReg, "strd<c> <Rt>, <Rt2>, [<Rn>, +/-<Rm>]{!}"},
   12464         { 0x0e100f00, 0x0c000b00, ARMvAll,       eEncodingA1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVSTM, "vstm{mode}<c> <Rn>{!} <list>"},
   12465         { 0x0e100f00, 0x0c000a00, ARMvAll,       eEncodingA2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVSTM, "vstm{mode}<c> <Rn>{!} <list>"},
   12466         { 0x0f300f00, 0x0d000b00, ARMvAll,       eEncodingA1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVSTR, "vstr<c> <Dd> [<Rn>{,#+/-<imm>}]"},
   12467         { 0x0f300f00, 0x0d000a00, ARMvAll,       eEncodingA2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVSTR, "vstr<c> <Sd> [<Rn>{,#+/-<imm>}]"},
   12468         { 0xffb00000, 0xf4000000, ARMvAll,       eEncodingA1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVST1Multiple, "vst1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12469         { 0xffb00300, 0xf4800000, ARMvAll,       eEncodingA1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVST1Single, "vst1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12470 
   12471         //----------------------------------------------------------------------
   12472         // Other instructions
   12473         //----------------------------------------------------------------------
   12474         { 0x0fff00f0, 0x06af00f0, ARMV6_ABOVE,  eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSXTB, "sxtb<c> <Rd>,<Rm>{,<rotation>}" },
   12475         { 0x0fff00f0, 0x06bf0070, ARMV6_ABOVE,  eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSXTH, "sxth<c> <Rd>,<Rm>{,<rotation>}" },
   12476         { 0x0fff00f0, 0x06ef0070, ARMV6_ABOVE,  eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateUXTB, "uxtb<c> <Rd>,<Rm>{,<rotation>}" },
   12477         { 0x0fff00f0, 0x06ff0070, ARMV6_ABOVE,  eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateUXTH, "uxth<c> <Rd>,<Rm>{,<rotation>}" },
   12478         { 0xfe500000, 0xf8100000, ARMV6_ABOVE,  eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRFE, "rfe{<amode>} <Rn>{!}" }
   12479 
   12480     };
   12481     static const size_t k_num_arm_opcodes = sizeof(g_arm_opcodes)/sizeof(ARMOpcode);
   12482 
   12483     for (size_t i=0; i<k_num_arm_opcodes; ++i)
   12484     {
   12485         if ((g_arm_opcodes[i].mask & opcode) == g_arm_opcodes[i].value &&
   12486             (g_arm_opcodes[i].variants & arm_isa) != 0)
   12487             return &g_arm_opcodes[i];
   12488     }
   12489     return NULL;
   12490 }
   12491 
   12492 
   12493 EmulateInstructionARM::ARMOpcode*
   12494 EmulateInstructionARM::GetThumbOpcodeForInstruction (const uint32_t opcode, uint32_t arm_isa)
   12495 {
   12496 
   12497     static ARMOpcode
   12498     g_thumb_opcodes[] =
   12499     {
   12500         //----------------------------------------------------------------------
   12501         // Prologue instructions
   12502         //----------------------------------------------------------------------
   12503 
   12504         // push register(s)
   12505         { 0xfffffe00, 0x0000b400, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulatePUSH, "push <registers>" },
   12506         { 0xffff0000, 0xe92d0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulatePUSH, "push.w <registers>" },
   12507         { 0xffff0fff, 0xf84d0d04, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulatePUSH, "push.w <register>" },
   12508 
   12509         // set r7 to point to a stack offset
   12510         { 0xffffff00, 0x0000af00, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDRdSPImm, "add r7, sp, #imm" },
   12511         // copy the stack pointer to r7
   12512         { 0xffffffff, 0x0000466f, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMOVRdSP, "mov r7, sp" },
   12513         // move from high register to low register (comes after "mov r7, sp" to resolve ambiguity)
   12514         { 0xffffffc0, 0x00004640, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMOVLowHigh, "mov r0-r7, r8-r15" },
   12515 
   12516         // PC-relative load into register (see also EmulateADDSPRm)
   12517         { 0xfffff800, 0x00004800, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRRtPCRelative, "ldr <Rt>, [PC, #imm]"},
   12518 
   12519         // adjust the stack pointer
   12520         { 0xffffff87, 0x00004485, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDSPRm, "add sp, <Rm>"},
   12521         { 0xffffff80, 0x0000b080, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSUBSPImm, "sub sp, sp, #imm"},
   12522         { 0xfbef8f00, 0xf1ad0d00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "sub.w sp, sp, #<const>"},
   12523         { 0xfbff8f00, 0xf2ad0d00, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "subw sp, sp, #imm12"},
   12524         { 0xffef8000, 0xebad0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPReg, "sub{s}<c> <Rd>, sp, <Rm>{,<shift>}" },
   12525 
   12526         // vector push consecutive extension register(s)
   12527         { 0xffbf0f00, 0xed2d0b00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPUSH, "vpush.64 <list>"},
   12528         { 0xffbf0f00, 0xed2d0a00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPUSH, "vpush.32 <list>"},
   12529 
   12530         //----------------------------------------------------------------------
   12531         // Epilogue instructions
   12532         //----------------------------------------------------------------------
   12533 
   12534         { 0xfffff800, 0x0000a800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDSPImm, "add<c> <Rd>, sp, #imm"},
   12535         { 0xffffff80, 0x0000b000, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDSPImm, "add sp, #imm"},
   12536         { 0xfffffe00, 0x0000bc00, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulatePOP, "pop <registers>"},
   12537         { 0xffff0000, 0xe8bd0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulatePOP, "pop.w <registers>" },
   12538         { 0xffff0fff, 0xf85d0d04, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulatePOP, "pop.w <register>" },
   12539         { 0xffbf0f00, 0xecbd0b00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPOP, "vpop.64 <list>"},
   12540         { 0xffbf0f00, 0xecbd0a00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateVPOP, "vpop.32 <list>"},
   12541 
   12542         //----------------------------------------------------------------------
   12543         // Supervisor Call (previously Software Interrupt)
   12544         //----------------------------------------------------------------------
   12545         { 0xffffff00, 0x0000df00, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSVC, "svc #imm8"},
   12546 
   12547         //----------------------------------------------------------------------
   12548         // If Then makes up to four following instructions conditional.
   12549         //----------------------------------------------------------------------
   12550         // The next 5 opcode _must_ come before the if then instruction
   12551         { 0xffffffff, 0x0000bf00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateNop, "nop"},
   12552         { 0xffffffff, 0x0000bf10, ARMV7_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateNop, "nop YIELD (yield hint)"},
   12553         { 0xffffffff, 0x0000bf20, ARMV7_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateNop, "nop WFE (wait for event hint)"},
   12554         { 0xffffffff, 0x0000bf30, ARMV7_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateNop, "nop WFI (wait for interrupt hint)"},
   12555         { 0xffffffff, 0x0000bf40, ARMV7_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateNop, "nop SEV (send event hint)"},
   12556         { 0xffffff00, 0x0000bf00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateIT, "it{<x>{<y>{<z>}}} <firstcond>"},
   12557 
   12558         //----------------------------------------------------------------------
   12559         // Branch instructions
   12560         //----------------------------------------------------------------------
   12561         // To resolve ambiguity, "b<c> #imm8" should come after "svc #imm8".
   12562         { 0xfffff000, 0x0000d000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateB, "b<c> #imm8 (outside IT)"},
   12563         { 0xfffff800, 0x0000e000, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateB, "b<c> #imm11 (outside or last in IT)"},
   12564         { 0xf800d000, 0xf0008000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateB, "b<c>.w #imm8 (outside IT)"},
   12565         { 0xf800d000, 0xf0009000, ARMV6T2_ABOVE, eEncodingT4, No_VFP, eSize32, &EmulateInstructionARM::EmulateB, "b<c>.w #imm8 (outside or last in IT)"},
   12566         // J1 == J2 == 1
   12567         { 0xf800d000, 0xf000d000, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBLXImmediate, "bl <label>"},
   12568         // J1 == J2 == 1
   12569         { 0xf800d001, 0xf000c000, ARMV5_ABOVE,   eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateBLXImmediate, "blx <label>"},
   12570         { 0xffffff87, 0x00004780, ARMV5_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateBLXRm, "blx <Rm>"},
   12571         // for example, "bx lr"
   12572         { 0xffffff87, 0x00004700, ARMvAll,       eEncodingA1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBXRm, "bx <Rm>"},
   12573         // bxj
   12574         { 0xfff0ffff, 0xf3c08f00, ARMV5J_ABOVE,  eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBXJRm, "bxj <Rm>"},
   12575         // compare and branch
   12576         { 0xfffff500, 0x0000b100, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateCB, "cb{n}z <Rn>, <label>"},
   12577         // table branch byte
   12578         { 0xfff0fff0, 0xe8d0f000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTB, "tbb<c> <Rn>, <Rm>"},
   12579         // table branch halfword
   12580         { 0xfff0fff0, 0xe8d0f010, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTB, "tbh<c> <Rn>, <Rm>, lsl #1"},
   12581 
   12582         //----------------------------------------------------------------------
   12583         // Data-processing instructions
   12584         //----------------------------------------------------------------------
   12585         // adc (immediate)
   12586         { 0xfbe08000, 0xf1400000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateADCImm, "adc{s}<c> <Rd>, <Rn>, #<const>"},
   12587         // adc (register)
   12588         { 0xffffffc0, 0x00004140, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADCReg, "adcs|adc<c> <Rdn>, <Rm>"},
   12589         { 0xffe08000, 0xeb400000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateADCReg, "adc{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12590         // add (register)
   12591         { 0xfffffe00, 0x00001800, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDReg, "adds|add<c> <Rd>, <Rn>, <Rm>"},
   12592         // Make sure "add sp, <Rm>" comes before this instruction, so there's no ambiguity decoding the two.
   12593         { 0xffffff00, 0x00004400, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDReg, "add<c> <Rdn>, <Rm>"},
   12594         // adr
   12595         { 0xfffff800, 0x0000a000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADR, "add<c> <Rd>, PC, #<const>"},
   12596         { 0xfbff8000, 0xf2af0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateADR, "sub<c> <Rd>, PC, #<const>"},
   12597         { 0xfbff8000, 0xf20f0000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateADR, "add<c> <Rd>, PC, #<const>"},
   12598         // and (immediate)
   12599         { 0xfbe08000, 0xf0000000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateANDImm, "and{s}<c> <Rd>, <Rn>, #<const>"},
   12600         // and (register)
   12601         { 0xffffffc0, 0x00004000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateANDReg, "ands|and<c> <Rdn>, <Rm>"},
   12602         { 0xffe08000, 0xea000000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateANDReg, "and{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12603         // bic (immediate)
   12604         { 0xfbe08000, 0xf0200000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateBICImm, "bic{s}<c> <Rd>, <Rn>, #<const>"},
   12605         // bic (register)
   12606         { 0xffffffc0, 0x00004380, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateBICReg, "bics|bic<c> <Rdn>, <Rm>"},
   12607         { 0xffe08000, 0xea200000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateBICReg, "bic{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12608         // eor (immediate)
   12609         { 0xfbe08000, 0xf0800000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateEORImm, "eor{s}<c> <Rd>, <Rn>, #<const>"},
   12610         // eor (register)
   12611         { 0xffffffc0, 0x00004040, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateEORReg, "eors|eor<c> <Rdn>, <Rm>"},
   12612         { 0xffe08000, 0xea800000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateEORReg, "eor{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12613         // orr (immediate)
   12614         { 0xfbe08000, 0xf0400000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateORRImm, "orr{s}<c> <Rd>, <Rn>, #<const>"},
   12615         // orr (register)
   12616         { 0xffffffc0, 0x00004300, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateORRReg, "orrs|orr<c> <Rdn>, <Rm>"},
   12617         { 0xffe08000, 0xea400000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateORRReg, "orr{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12618         // rsb (immediate)
   12619         { 0xffffffc0, 0x00004240, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateRSBImm, "rsbs|rsb<c> <Rd>, <Rn>, #0"},
   12620         { 0xfbe08000, 0xf1c00000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSBImm, "rsb{s}<c>.w <Rd>, <Rn>, #<const>"},
   12621         // rsb (register)
   12622         { 0xffe08000, 0xea400000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRSBReg, "rsb{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12623         // sbc (immediate)
   12624         { 0xfbe08000, 0xf1600000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSBCImm, "sbc{s}<c> <Rd>, <Rn>, #<const>"},
   12625         // sbc (register)
   12626         { 0xffffffc0, 0x00004180, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSBCReg, "sbcs|sbc<c> <Rdn>, <Rm>"},
   12627         { 0xffe08000, 0xeb600000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSBCReg, "sbc{s}<c>.w <Rd>, <Rn>, <Rm> {,<shift>}"},
   12628         // add (immediate, Thumb)
   12629         { 0xfffffe00, 0x00001c00, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDImmThumb, "adds|add<c> <Rd>,<Rn>,#<imm3>" },
   12630         { 0xfffff800, 0x00003000, ARMV4T_ABOVE,  eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateADDImmThumb, "adds|add<c> <Rdn>,#<imm8>" },
   12631         { 0xfbe08000, 0xf1000000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDImmThumb, "add{s}<c>.w <Rd>,<Rn>,#<const>" },
   12632         { 0xfbf08000, 0xf2000000, ARMV6T2_ABOVE, eEncodingT4, No_VFP, eSize32, &EmulateInstructionARM::EmulateADDImmThumb, "addw<c> <Rd>,<Rn>,#<imm12>" },
   12633         // sub (immediate, Thumb)
   12634         { 0xfffffe00, 0x00001e00, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSUBImmThumb, "subs|sub<c> <Rd>, <Rn> #imm3"},
   12635         { 0xfffff800, 0x00003800, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateSUBImmThumb, "subs|sub<c> <Rdn>, #imm8"},
   12636         { 0xfbe08000, 0xf1a00000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBImmThumb, "sub{s}<c>.w <Rd>, <Rn>, #<const>"},
   12637         { 0xfbf08000, 0xf2a00000, ARMV6T2_ABOVE, eEncodingT4, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBImmThumb, "subw<c> <Rd>, <Rn>, #imm12"},
   12638         // sub (sp minus immediate)
   12639         { 0xfbef8000, 0xf1ad0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "sub{s}.w <Rd>, sp, #<const>"},
   12640         { 0xfbff8000, 0xf2ad0000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPImm, "subw<c> <Rd>, sp, #imm12"},
   12641         // sub (register)
   12642         { 0xfffffe00, 0x00001a00, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSUBReg, "subs|sub<c> <Rd>, <Rn>, <Rm>"},
   12643         { 0xffe08000, 0xeba00000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBReg, "sub{s}<c>.w <Rd>, <Rn>, <Rm>{,<shift>}"},
   12644         // teq (immediate)
   12645         { 0xfbf08f00, 0xf0900f00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTEQImm, "teq<c> <Rn>, #<const>"},
   12646         // teq (register)
   12647         { 0xfff08f00, 0xea900f00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTEQReg, "teq<c> <Rn>, <Rm> {,<shift>}"},
   12648         // tst (immediate)
   12649         { 0xfbf08f00, 0xf0100f00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateTSTImm, "tst<c> <Rn>, #<const>"},
   12650         // tst (register)
   12651         { 0xffffffc0, 0x00004200, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateTSTReg, "tst<c> <Rdn>, <Rm>"},
   12652         { 0xfff08f00, 0xea100f00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateTSTReg, "tst<c>.w <Rn>, <Rm> {,<shift>}"},
   12653 
   12654 
   12655         // move from high register to high register
   12656         { 0xffffff00, 0x00004600, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMOVRdRm, "mov<c> <Rd>, <Rm>"},
   12657         // move from low register to low register
   12658         { 0xffffffc0, 0x00000000, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateMOVRdRm, "movs <Rd>, <Rm>"},
   12659         // mov{s}<c>.w <Rd>, <Rm>
   12660         { 0xffeff0f0, 0xea4f0000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdRm, "mov{s}<c>.w <Rd>, <Rm>"},
   12661         // move immediate
   12662         { 0xfffff800, 0x00002000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMOVRdImm, "movs|mov<c> <Rd>, #imm8"},
   12663         { 0xfbef8000, 0xf04f0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdImm, "mov{s}<c>.w <Rd>, #<const>"},
   12664         { 0xfbf08000, 0xf2400000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateMOVRdImm, "movw<c> <Rd>,#<imm16>"},
   12665         // mvn (immediate)
   12666         { 0xfbef8000, 0xf06f0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateMVNImm, "mvn{s} <Rd>, #<const>"},
   12667         // mvn (register)
   12668         { 0xffffffc0, 0x000043c0, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMVNReg, "mvns|mvn<c> <Rd>, <Rm>"},
   12669         { 0xffef8000, 0xea6f0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateMVNReg, "mvn{s}<c>.w <Rd>, <Rm> {,<shift>}"},
   12670         // cmn (immediate)
   12671         { 0xfbf08f00, 0xf1100f00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMNImm, "cmn<c> <Rn>, #<const>"},
   12672         // cmn (register)
   12673         { 0xffffffc0, 0x000042c0, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateCMNReg, "cmn<c> <Rn>, <Rm>"},
   12674         { 0xfff08f00, 0xeb100f00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMNReg, "cmn<c> <Rn>, <Rm> {,<shift>}"},
   12675         // cmp (immediate)
   12676         { 0xfffff800, 0x00002800, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateCMPImm, "cmp<c> <Rn>, #imm8"},
   12677         { 0xfbf08f00, 0xf1b00f00, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateCMPImm, "cmp<c>.w <Rn>, #<const>"},
   12678         // cmp (register) (Rn and Rm both from r0-r7)
   12679         { 0xffffffc0, 0x00004280, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateCMPReg, "cmp<c> <Rn>, <Rm>"},
   12680         // cmp (register) (Rn and Rm not both from r0-r7)
   12681         { 0xffffff00, 0x00004500, ARMvAll,       eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateCMPReg, "cmp<c> <Rn>, <Rm>"},
   12682         // asr (immediate)
   12683         { 0xfffff800, 0x00001000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateASRImm, "asrs|asr<c> <Rd>, <Rm>, #imm"},
   12684         { 0xffef8030, 0xea4f0020, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateASRImm, "asr{s}<c>.w <Rd>, <Rm>, #imm"},
   12685         // asr (register)
   12686         { 0xffffffc0, 0x00004100, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateASRReg, "asrs|asr<c> <Rdn>, <Rm>"},
   12687         { 0xffe0f0f0, 0xfa40f000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateASRReg, "asr{s}<c>.w <Rd>, <Rn>, <Rm>"},
   12688         // lsl (immediate)
   12689         { 0xfffff800, 0x00000000, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLSLImm, "lsls|lsl<c> <Rd>, <Rm>, #imm"},
   12690         { 0xffef8030, 0xea4f0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSLImm, "lsl{s}<c>.w <Rd>, <Rm>, #imm"},
   12691         // lsl (register)
   12692         { 0xffffffc0, 0x00004080, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLSLReg, "lsls|lsl<c> <Rdn>, <Rm>"},
   12693         { 0xffe0f0f0, 0xfa00f000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSLReg, "lsl{s}<c>.w <Rd>, <Rn>, <Rm>"},
   12694         // lsr (immediate)
   12695         { 0xfffff800, 0x00000800, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLSRImm, "lsrs|lsr<c> <Rd>, <Rm>, #imm"},
   12696         { 0xffef8030, 0xea4f0010, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSRImm, "lsr{s}<c>.w <Rd>, <Rm>, #imm"},
   12697         // lsr (register)
   12698         { 0xffffffc0, 0x000040c0, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLSRReg, "lsrs|lsr<c> <Rdn>, <Rm>"},
   12699         { 0xffe0f0f0, 0xfa20f000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLSRReg, "lsr{s}<c>.w <Rd>, <Rn>, <Rm>"},
   12700         // rrx is a special case encoding of ror (immediate)
   12701         { 0xffeff0f0, 0xea4f0030, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRRX, "rrx{s}<c>.w <Rd>, <Rm>"},
   12702         // ror (immediate)
   12703         { 0xffef8030, 0xea4f0030, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRORImm, "ror{s}<c>.w <Rd>, <Rm>, #imm"},
   12704         // ror (register)
   12705         { 0xffffffc0, 0x000041c0, ARMvAll,       eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateRORReg, "rors|ror<c> <Rdn>, <Rm>"},
   12706         { 0xffe0f0f0, 0xfa60f000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateRORReg, "ror{s}<c>.w <Rd>, <Rn>, <Rm>"},
   12707         // mul
   12708         { 0xffffffc0, 0x00004340, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateMUL, "muls <Rdm>,<Rn>,<Rdm>" },
   12709         // mul
   12710         { 0xfff0f0f0, 0xfb00f000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateMUL, "mul<c> <Rd>,<Rn>,<Rm>" },
   12711 
   12712         // subs pc, lr and related instructions
   12713         { 0xffffff00, 0xf3de8f00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSUBSPcLrEtc, "SUBS<c> PC, LR, #<imm8>" },
   12714 
   12715         //----------------------------------------------------------------------
   12716         // RFE instructions  *** IMPORTANT *** THESE MUST BE LISTED **BEFORE** THE LDM.. Instructions in this table;
   12717         // otherwise the wrong instructions will be selected.
   12718         //----------------------------------------------------------------------
   12719 
   12720         { 0xffd0ffff, 0xe810c000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateRFE, "rfedb<c> <Rn>{!}" },
   12721         { 0xffd0ffff, 0xe990c000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateRFE, "rfe{ia}<c> <Rn>{!}" },
   12722 
   12723         //----------------------------------------------------------------------
   12724         // Load instructions
   12725         //----------------------------------------------------------------------
   12726         { 0xfffff800, 0x0000c800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDM, "ldm<c> <Rn>{!} <registers>" },
   12727         { 0xffd02000, 0xe8900000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDM, "ldm<c>.w <Rn>{!} <registers>" },
   12728         { 0xffd00000, 0xe9100000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDMDB, "ldmdb<c> <Rn>{!} <registers>" },
   12729         { 0xfffff800, 0x00006800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRRtRnImm, "ldr<c> <Rt>, [<Rn>{,#imm}]"},
   12730         { 0xfffff800, 0x00009800, ARMV4T_ABOVE,  eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRRtRnImm, "ldr<c> <Rt>, [SP{,#imm}]"},
   12731         { 0xfff00000, 0xf8d00000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRRtRnImm, "ldr<c>.w <Rt>, [<Rn>{,#imm12}]"},
   12732         { 0xfff00800, 0xf8500800, ARMV6T2_ABOVE, eEncodingT4, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRRtRnImm, "ldr<c> <Rt>, [<Rn>{,#+/-<imm8>}]{!}"},
   12733                   // Thumb2 PC-relative load into register
   12734         { 0xff7f0000, 0xf85f0000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRRtPCRelative, "ldr<c>.w <Rt>, [PC, +/-#imm}]"},
   12735         { 0xfffffe00, 0x00005800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRRegister, "ldr<c> <Rt>, [<Rn>, <Rm>]" },
   12736         { 0xfff00fc0, 0xf8500000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRRegister, "ldr<c>.w <Rt>, [<Rn>,<Rm>{,LSL #<imm2>}]" },
   12737         { 0xfffff800, 0x00007800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRBImmediate, "ldrb<c> <Rt>,[<Rn>{,#<imm5>}]" },
   12738         { 0xfff00000, 0xf8900000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBImmediate, "ldrb<c>.w <Rt>,[<Rn>{,#<imm12>}]" },
   12739         { 0xfff00800, 0xf8100800, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBImmediate, "ldrb<c> <Rt>,[<Rn>, #+/-<imm8>]{!}" },
   12740         { 0xff7f0000, 0xf81f0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBLiteral, "ldrb<c> <Rt>,[...]" },
   12741         { 0xfffffe00, 0x00005c00, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRBRegister, "ldrb<c> <Rt>,[<Rn>,<Rm>]" },
   12742         { 0xfff00fc0, 0xf8100000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRBRegister, "ldrb<c>.w <Rt>,[<Rn>,<Rm>{,LSL #imm2>}]" },
   12743         { 0xfffff800, 0x00008800, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRHImmediate, "ldrh<c> <Rt>, [<Rn>{,#<imm>}]"  },
   12744         { 0xfff00000, 0xf8b00000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHImmediate, "ldrh<c>.w <Rt>,[<Rn>{,#<imm12>}]" },
   12745         { 0xfff00800, 0xf8300800, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHImmediate, "ldrh<c> <Rt>,[<Rn>,#+/-<imm8>]{!}"  },
   12746         { 0xff7f0000, 0xf83f0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHLiteral, "ldrh<c> <Rt>, <label>" },
   12747         { 0xfffffe00, 0x00005a00, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRHRegister, "ldrh<c> <Rt>, [<Rn>,<Rm>]" },
   12748         { 0xfff00fc0, 0xf8300000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRHRegister, "ldrh<c>.w <Rt>,[<Rn>,<Rm>{,LSL #<imm2>}]" },
   12749         { 0xfff00000, 0xf9900000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBImmediate, "ldrsb<c> <Rt>,[<Rn>,#<imm12>]" },
   12750         { 0xfff00800, 0xf9100800, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBImmediate, "ldrsb<c> <Rt>,[<Rn>,#+/-<imm8>]" },
   12751         { 0xff7f0000, 0xf91f0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBLiteral, "ldrsb<c> <Rt>, <label>" },
   12752         { 0xfffffe00, 0x00005600, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRSBRegister, "ldrsb<c> <Rt>,[<Rn>,<Rm>]" },
   12753         { 0xfff00fc0, 0xf9100000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSBRegister, "ldrsb<c>.w <Rt>,[<Rn>,<Rm>{,LSL #imm2>}]"  },
   12754         { 0xfff00000, 0xf9b00000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHImmediate, "ldrsh<c> <Rt>,[<Rn>,#<imm12>]" },
   12755         { 0xfff00800, 0xf9300800, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHImmediate, "ldrsh<c> <Rt>,[<Rn>,#+/-<imm8>]" },
   12756         { 0xff7f0000, 0xf93f0000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHLiteral, "ldrsh<c> <Rt>,<label>" },
   12757         { 0xfffffe00, 0x00005e00, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateLDRSHRegister, "ldrsh<c> <Rt>,[<Rn>,<Rm>]" },
   12758         { 0xfff00fc0, 0xf9300000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRSHRegister, "ldrsh<c>.w <Rt>,[<Rn>,<Rm>{,LSL #<imm2>}]" },
   12759         { 0xfe500000, 0xe8500000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateLDRDImmediate, "ldrd<c> <Rt>, <Rt2>, [<Rn>,#+/-<imm>]!"},
   12760         { 0xfe100f00, 0xec100b00, ARMvAll,       eEncodingT1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVLDM, "vldm{mode}<c> <Rn>{!}, <list>"},
   12761         { 0xfe100f00, 0xec100a00, ARMvAll,       eEncodingT2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVLDM, "vldm{mode}<c> <Rn>{!}, <list>" },
   12762         { 0xffe00f00, 0xed100b00, ARMvAll,       eEncodingT1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVLDR, "vldr<c> <Dd>, [<Rn>{,#+/-<imm>}]"},
   12763         { 0xff300f00, 0xed100a00, ARMvAll,       eEncodingT2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVLDR, "vldr<c> <Sd>, {<Rn>{,#+/-<imm>}]"},
   12764         { 0xffb00000, 0xf9200000, ARMvAll,       eEncodingT1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1Multiple, "vld1<c>.<size> <list>, [<Rn>{@<align>}],<Rm>"},
   12765         { 0xffb00300, 0xf9a00000, ARMvAll,       eEncodingT1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1Single, "vld1<c>.<size> <list>, [<Rn>{@<align>}],<Rm>"},
   12766         { 0xffb00f00, 0xf9a00c00, ARMvAll,       eEncodingT1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVLD1SingleAll, "vld1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12767 
   12768         //----------------------------------------------------------------------
   12769         // Store instructions
   12770         //----------------------------------------------------------------------
   12771         { 0xfffff800, 0x0000c000, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTM, "stm<c> <Rn>{!} <registers>" },
   12772         { 0xffd00000, 0xe8800000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTM, "stm<c>.w <Rn>{!} <registers>" },
   12773         { 0xffd00000, 0xe9000000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTMDB, "stmdb<c> <Rn>{!} <registers>" },
   12774         { 0xfffff800, 0x00006000, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTRThumb, "str<c> <Rt>, [<Rn>{,#<imm>}]" },
   12775         { 0xfffff800, 0x00009000, ARMV4T_ABOVE,  eEncodingT2, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTRThumb, "str<c> <Rt>, [SP,#<imm>]" },
   12776         { 0xfff00000, 0xf8c00000, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRThumb, "str<c>.w <Rt>, [<Rn>,#<imm12>]" },
   12777         { 0xfff00800, 0xf8400800, ARMV6T2_ABOVE, eEncodingT4, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRThumb, "str<c> <Rt>, [<Rn>,#+/-<imm8>]" },
   12778         { 0xfffffe00, 0x00005000, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTRRegister, "str<c> <Rt> ,{<Rn>, <Rm>]" },
   12779         { 0xfff00fc0, 0xf8400000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRRegister, "str<c>.w <Rt>, [<Rn>, <Rm> {lsl #imm2>}]" },
   12780         { 0xfffff800, 0x00007000, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTRBThumb, "strb<c> <Rt>, [<Rn>, #<imm5>]" },
   12781         { 0xfff00000, 0xf8800000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRBThumb, "strb<c>.w <Rt>, [<Rn>, #<imm12>]" },
   12782         { 0xfff00800, 0xf8000800, ARMV6T2_ABOVE, eEncodingT3, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRBThumb, "strb<c> <Rt> ,[<Rn>, #+/-<imm8>]{!}" },
   12783         { 0xfffffe00, 0x00005200, ARMV4T_ABOVE,  eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSTRHRegister, "strh<c> <Rt>,[<Rn>,<Rm>]" },
   12784         { 0xfff00fc0, 0xf8200000, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRHRegister, "strh<c>.w <Rt>,[<Rn>,<Rm>{,LSL #<imm2>}]" },
   12785         { 0xfff00000, 0xe8400000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTREX, "strex<c> <Rd>, <Rt>, [<Rn{,#<imm>}]" },
   12786         { 0xfe500000, 0xe8400000, ARMV6T2_ABOVE, eEncodingT1, No_VFP, eSize32, &EmulateInstructionARM::EmulateSTRDImm, "strd<c> <Rt>, <Rt2>, [<Rn>, #+/-<imm>]!"},
   12787         { 0xfe100f00, 0xec000b00, ARMvAll,       eEncodingT1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVSTM, "vstm{mode}<c> <Rn>{!}, <list>"},
   12788         { 0xfea00f00, 0xec000a00, ARMvAll,       eEncodingT2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVSTM, "vstm{mode}<c> <Rn>{!}, <list>"},
   12789         { 0xff300f00, 0xed000b00, ARMvAll,       eEncodingT1, VFPv2_ABOVE,  eSize32, &EmulateInstructionARM::EmulateVSTR, "vstr<c> <Dd>, [<Rn>{,#+/-<imm>}]"},
   12790         { 0xff300f00, 0xed000a00, ARMvAll,       eEncodingT2, VFPv2v3,      eSize32, &EmulateInstructionARM::EmulateVSTR, "vstr<c> <Sd>, [<Rn>{,#+/-<imm>}]"},
   12791         { 0xffb00000, 0xf9000000, ARMvAll,       eEncodingT1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVST1Multiple, "vst1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12792         { 0xffb00300, 0xf9800000, ARMvAll,       eEncodingT1, AdvancedSIMD, eSize32, &EmulateInstructionARM::EmulateVST1Single, "vst1<c>.<size> <list>, [<Rn>{@<align>}], <Rm>"},
   12793 
   12794         //----------------------------------------------------------------------
   12795         // Other instructions
   12796         //----------------------------------------------------------------------
   12797         { 0xffffffc0, 0x0000b240, ARMV6_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSXTB, "sxtb<c> <Rd>,<Rm>" },
   12798         { 0xfffff080, 0xfa4ff080, ARMV6_ABOVE,   eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSXTB, "sxtb<c>.w <Rd>,<Rm>{,<rotation>}" },
   12799         { 0xffffffc0, 0x0000b200, ARMV6_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateSXTH, "sxth<c> <Rd>,<Rm>" },
   12800         { 0xfffff080, 0xfa0ff080, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateSXTH, "sxth<c>.w <Rd>,<Rm>{,<rotation>}" },
   12801         { 0xffffffc0, 0x0000b2c0, ARMV6_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateUXTB, "uxtb<c> <Rd>,<Rm>" },
   12802         { 0xfffff080, 0xfa5ff080, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateUXTB, "uxtb<c>.w <Rd>,<Rm>{,<rotation>}" },
   12803         { 0xffffffc0, 0x0000b280, ARMV6_ABOVE,   eEncodingT1, No_VFP, eSize16, &EmulateInstructionARM::EmulateUXTH, "uxth<c> <Rd>,<Rm>" },
   12804         { 0xfffff080, 0xfa1ff080, ARMV6T2_ABOVE, eEncodingT2, No_VFP, eSize32, &EmulateInstructionARM::EmulateUXTH, "uxth<c>.w <Rd>,<Rm>{,<rotation>}" },
   12805     };
   12806 
   12807     const size_t k_num_thumb_opcodes = sizeof(g_thumb_opcodes)/sizeof(ARMOpcode);
   12808     for (size_t i=0; i<k_num_thumb_opcodes; ++i)
   12809     {
   12810         if ((g_thumb_opcodes[i].mask & opcode) == g_thumb_opcodes[i].value &&
   12811             (g_thumb_opcodes[i].variants & arm_isa) != 0)
   12812             return &g_thumb_opcodes[i];
   12813     }
   12814     return NULL;
   12815 }
   12816 
   12817 bool
   12818 EmulateInstructionARM::SetArchitecture (const ArchSpec &arch)
   12819 {
   12820     m_arch = arch;
   12821     m_arm_isa = 0;
   12822     const char *arch_cstr = arch.GetArchitectureName ();
   12823     if (arch_cstr)
   12824     {
   12825         if      (0 == ::strcasecmp(arch_cstr, "armv4t"))    m_arm_isa = ARMv4T;
   12826         else if (0 == ::strcasecmp(arch_cstr, "armv5tej"))  m_arm_isa = ARMv5TEJ;
   12827         else if (0 == ::strcasecmp(arch_cstr, "armv5te"))   m_arm_isa = ARMv5TE;
   12828         else if (0 == ::strcasecmp(arch_cstr, "armv5t"))    m_arm_isa = ARMv5T;
   12829         else if (0 == ::strcasecmp(arch_cstr, "armv6k"))    m_arm_isa = ARMv6K;
   12830         else if (0 == ::strcasecmp(arch_cstr, "armv6t2"))   m_arm_isa = ARMv6T2;
   12831         else if (0 == ::strcasecmp(arch_cstr, "armv7s"))    m_arm_isa = ARMv7S;
   12832         else if (0 == ::strcasecmp(arch_cstr, "arm"))       m_arm_isa = ARMvAll;
   12833         else if (0 == ::strcasecmp(arch_cstr, "thumb"))     m_arm_isa = ARMvAll;
   12834         else if (0 == ::strncasecmp(arch_cstr,"armv4", 5))  m_arm_isa = ARMv4;
   12835         else if (0 == ::strncasecmp(arch_cstr,"armv6", 5))  m_arm_isa = ARMv6;
   12836         else if (0 == ::strncasecmp(arch_cstr,"armv7", 5))  m_arm_isa = ARMv7;
   12837         else if (0 == ::strncasecmp(arch_cstr,"armv8", 5))  m_arm_isa = ARMv8;
   12838     }
   12839     return m_arm_isa != 0;
   12840 }
   12841 
   12842 bool
   12843 EmulateInstructionARM::SetInstruction (const Opcode &insn_opcode, const Address &inst_addr, Target *target)
   12844 {
   12845     if (EmulateInstruction::SetInstruction (insn_opcode, inst_addr, target))
   12846     {
   12847         if (m_arch.GetTriple().getArch() == llvm::Triple::thumb)
   12848             m_opcode_mode = eModeThumb;
   12849         else
   12850         {
   12851             AddressClass addr_class = inst_addr.GetAddressClass();
   12852 
   12853             if ((addr_class == eAddressClassCode) || (addr_class == eAddressClassUnknown))
   12854                 m_opcode_mode = eModeARM;
   12855             else if (addr_class == eAddressClassCodeAlternateISA)
   12856                 m_opcode_mode = eModeThumb;
   12857             else
   12858                 return false;
   12859         }
   12860         if (m_opcode_mode == eModeThumb)
   12861             m_opcode_cpsr = CPSR_MODE_USR | MASK_CPSR_T;
   12862         else
   12863             m_opcode_cpsr = CPSR_MODE_USR;
   12864         return true;
   12865     }
   12866     return false;
   12867 }
   12868 
   12869 bool
   12870 EmulateInstructionARM::ReadInstruction ()
   12871 {
   12872     bool success = false;
   12873     m_opcode_cpsr = ReadRegisterUnsigned (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FLAGS, 0, &success);
   12874     if (success)
   12875     {
   12876         addr_t pc = ReadRegisterUnsigned (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, LLDB_INVALID_ADDRESS, &success);
   12877         if (success)
   12878         {
   12879             Context read_inst_context;
   12880             read_inst_context.type = eContextReadOpcode;
   12881             read_inst_context.SetNoArgs ();
   12882 
   12883             if (m_opcode_cpsr & MASK_CPSR_T)
   12884             {
   12885                 m_opcode_mode = eModeThumb;
   12886                 uint32_t thumb_opcode = MemARead(read_inst_context, pc, 2, 0, &success);
   12887 
   12888                 if (success)
   12889                 {
   12890                     if ((thumb_opcode & 0xe000) != 0xe000 || ((thumb_opcode & 0x1800u) == 0))
   12891                     {
   12892                         m_opcode.SetOpcode16 (thumb_opcode);
   12893                     }
   12894                     else
   12895                     {
   12896                         m_opcode.SetOpcode32 ((thumb_opcode << 16) | MemARead(read_inst_context, pc + 2, 2, 0, &success));
   12897                     }
   12898                 }
   12899             }
   12900             else
   12901             {
   12902                 m_opcode_mode = eModeARM;
   12903                 m_opcode.SetOpcode32 (MemARead(read_inst_context, pc, 4, 0, &success));
   12904             }
   12905         }
   12906     }
   12907     if (!success)
   12908     {
   12909         m_opcode_mode = eModeInvalid;
   12910         m_addr = LLDB_INVALID_ADDRESS;
   12911     }
   12912     return success;
   12913 }
   12914 
   12915 uint32_t
   12916 EmulateInstructionARM::ArchVersion ()
   12917 {
   12918     return m_arm_isa;
   12919 }
   12920 
   12921 bool
   12922 EmulateInstructionARM::ConditionPassed (const uint32_t opcode, bool *is_conditional)
   12923 {
   12924    // If we are ignoring conditions, then always return true.
   12925    // this allows us to iterate over disassembly code and still
   12926    // emulate an instruction even if we don't have all the right
   12927    // bits set in the CPSR register...
   12928     if (m_ignore_conditions)
   12929         return true;
   12930 
   12931     if (is_conditional)
   12932         *is_conditional = true;
   12933 
   12934     const uint32_t cond = CurrentCond (opcode);
   12935 
   12936     if (cond == UINT32_MAX)
   12937         return false;
   12938 
   12939     bool result = false;
   12940     switch (UnsignedBits(cond, 3, 1))
   12941     {
   12942     case 0:
   12943 		if (m_opcode_cpsr == 0)
   12944 			result = true;
   12945         else
   12946             result = (m_opcode_cpsr & MASK_CPSR_Z) != 0;
   12947 		break;
   12948     case 1:
   12949         if (m_opcode_cpsr == 0)
   12950             result = true;
   12951         else
   12952             result = (m_opcode_cpsr & MASK_CPSR_C) != 0;
   12953 		break;
   12954     case 2:
   12955         if (m_opcode_cpsr == 0)
   12956             result = true;
   12957         else
   12958             result = (m_opcode_cpsr & MASK_CPSR_N) != 0;
   12959 		break;
   12960     case 3:
   12961         if (m_opcode_cpsr == 0)
   12962             result = true;
   12963         else
   12964             result = (m_opcode_cpsr & MASK_CPSR_V) != 0;
   12965 		break;
   12966     case 4:
   12967         if (m_opcode_cpsr == 0)
   12968             result = true;
   12969         else
   12970             result = ((m_opcode_cpsr & MASK_CPSR_C) != 0) && ((m_opcode_cpsr & MASK_CPSR_Z) == 0);
   12971 		break;
   12972     case 5:
   12973         if (m_opcode_cpsr == 0)
   12974             result = true;
   12975         else
   12976 		{
   12977             bool n = (m_opcode_cpsr & MASK_CPSR_N);
   12978             bool v = (m_opcode_cpsr & MASK_CPSR_V);
   12979             result = n == v;
   12980         }
   12981         break;
   12982     case 6:
   12983         if (m_opcode_cpsr == 0)
   12984             result = true;
   12985         else
   12986 		{
   12987             bool n = (m_opcode_cpsr & MASK_CPSR_N);
   12988             bool v = (m_opcode_cpsr & MASK_CPSR_V);
   12989             result = n == v && ((m_opcode_cpsr & MASK_CPSR_Z) == 0);
   12990         }
   12991         break;
   12992     case 7:
   12993         // Always execute (cond == 0b1110, or the special 0b1111 which gives
   12994         // opcodes different meanings, but always means execution happpens.
   12995         if (is_conditional)
   12996             *is_conditional = false;
   12997         result = true;
   12998         break;
   12999     }
   13000 
   13001     if (cond & 1)
   13002         result = !result;
   13003     return result;
   13004 }
   13005 
   13006 uint32_t
   13007 EmulateInstructionARM::CurrentCond (const uint32_t opcode)
   13008 {
   13009     switch (m_opcode_mode)
   13010     {
   13011     case eModeInvalid:
   13012         break;
   13013 
   13014     case eModeARM:
   13015         return UnsignedBits(opcode, 31, 28);
   13016 
   13017     case eModeThumb:
   13018         // For T1 and T3 encodings of the Branch instruction, it returns the 4-bit
   13019         // 'cond' field of the encoding.
   13020         {
   13021             const uint32_t byte_size = m_opcode.GetByteSize();
   13022             if (byte_size == 2)
   13023             {
   13024                 if (Bits32(opcode, 15, 12) == 0x0d && Bits32(opcode, 11, 7) != 0x0f)
   13025                     return Bits32(opcode, 11, 7);
   13026             }
   13027             else if (byte_size == 4)
   13028             {
   13029                 if (Bits32(opcode, 31, 27) == 0x1e &&
   13030                     Bits32(opcode, 15, 14) == 0x02 &&
   13031                     Bits32(opcode, 12, 12) == 0x00 &&
   13032                     Bits32(opcode, 25, 22) <= 0x0d)
   13033                 {
   13034                     return Bits32(opcode, 25, 22);
   13035                 }
   13036             }
   13037             else
   13038                 // We have an invalid thumb instruction, let's bail out.
   13039                 break;
   13040 
   13041             return m_it_session.GetCond();
   13042         }
   13043     }
   13044     return UINT32_MAX;  // Return invalid value
   13045 }
   13046 
   13047 bool
   13048 EmulateInstructionARM::InITBlock()
   13049 {
   13050     return CurrentInstrSet() == eModeThumb && m_it_session.InITBlock();
   13051 }
   13052 
   13053 bool
   13054 EmulateInstructionARM::LastInITBlock()
   13055 {
   13056     return CurrentInstrSet() == eModeThumb && m_it_session.LastInITBlock();
   13057 }
   13058 
   13059 bool
   13060 EmulateInstructionARM::BadMode (uint32_t mode)
   13061 {
   13062 
   13063     switch (mode)
   13064     {
   13065         case 16: return false; // '10000'
   13066         case 17: return false; // '10001'
   13067         case 18: return false; // '10010'
   13068         case 19: return false; // '10011'
   13069         case 22: return false; // '10110'
   13070         case 23: return false; // '10111'
   13071         case 27: return false; // '11011'
   13072         case 31: return false; // '11111'
   13073         default: return true;
   13074     }
   13075     return true;
   13076 }
   13077 
   13078 bool
   13079 EmulateInstructionARM::CurrentModeIsPrivileged ()
   13080 {
   13081     uint32_t mode = Bits32 (m_opcode_cpsr, 4, 0);
   13082 
   13083     if (BadMode (mode))
   13084         return false;
   13085 
   13086     if (mode == 16)
   13087         return false;
   13088 
   13089     return true;
   13090 }
   13091 
   13092 void
   13093 EmulateInstructionARM::CPSRWriteByInstr (uint32_t value, uint32_t bytemask, bool affect_execstate)
   13094 {
   13095     bool privileged = CurrentModeIsPrivileged();
   13096 
   13097     uint32_t tmp_cpsr = Bits32 (m_opcode_cpsr, 23, 20) << 20;
   13098 
   13099     if (BitIsSet (bytemask, 3))
   13100     {
   13101         tmp_cpsr = tmp_cpsr | (Bits32 (value, 31, 27) << 27);
   13102         if (affect_execstate)
   13103             tmp_cpsr = tmp_cpsr | (Bits32 (value, 26, 24) << 24);
   13104     }
   13105 
   13106     if (BitIsSet (bytemask, 2))
   13107     {
   13108         tmp_cpsr = tmp_cpsr | (Bits32 (value, 19, 16) << 16);
   13109     }
   13110 
   13111     if (BitIsSet (bytemask, 1))
   13112     {
   13113         if (affect_execstate)
   13114             tmp_cpsr = tmp_cpsr | (Bits32 (value, 15, 10) << 10);
   13115         tmp_cpsr = tmp_cpsr | (Bit32 (value, 9) << 9);
   13116         if (privileged)
   13117             tmp_cpsr = tmp_cpsr | (Bit32 (value, 8) << 8);
   13118     }
   13119 
   13120     if (BitIsSet (bytemask, 0))
   13121     {
   13122         if (privileged)
   13123             tmp_cpsr = tmp_cpsr | (Bits32 (value, 7, 6) << 6);
   13124         if (affect_execstate)
   13125             tmp_cpsr = tmp_cpsr | (Bit32 (value, 5) << 5);
   13126         if (privileged)
   13127             tmp_cpsr = tmp_cpsr | Bits32 (value, 4, 0);
   13128     }
   13129 
   13130     m_opcode_cpsr = tmp_cpsr;
   13131 }
   13132 
   13133 
   13134 bool
   13135 EmulateInstructionARM::BranchWritePC (const Context &context, uint32_t addr)
   13136 {
   13137     addr_t target;
   13138 
   13139     // Check the current instruction set.
   13140     if (CurrentInstrSet() == eModeARM)
   13141         target = addr & 0xfffffffc;
   13142     else
   13143         target = addr & 0xfffffffe;
   13144 
   13145     if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, target))
   13146         return false;
   13147 
   13148     return true;
   13149 }
   13150 
   13151 // As a side effect, BXWritePC sets context.arg2 to eModeARM or eModeThumb by inspecting addr.
   13152 bool
   13153 EmulateInstructionARM::BXWritePC (Context &context, uint32_t addr)
   13154 {
   13155     addr_t target;
   13156     // If the CPSR is changed due to switching between ARM and Thumb ISETSTATE,
   13157     // we want to record it and issue a WriteRegister callback so the clients
   13158     // can track the mode changes accordingly.
   13159     bool cpsr_changed = false;
   13160 
   13161     if (BitIsSet(addr, 0))
   13162     {
   13163         if (CurrentInstrSet() != eModeThumb)
   13164         {
   13165             SelectInstrSet(eModeThumb);
   13166             cpsr_changed = true;
   13167         }
   13168         target = addr & 0xfffffffe;
   13169         context.SetISA (eModeThumb);
   13170     }
   13171     else if (BitIsClear(addr, 1))
   13172     {
   13173         if (CurrentInstrSet() != eModeARM)
   13174         {
   13175             SelectInstrSet(eModeARM);
   13176             cpsr_changed = true;
   13177         }
   13178         target = addr & 0xfffffffc;
   13179         context.SetISA (eModeARM);
   13180     }
   13181     else
   13182         return false; // address<1:0> == '10' => UNPREDICTABLE
   13183 
   13184     if (cpsr_changed)
   13185     {
   13186         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FLAGS, m_new_inst_cpsr))
   13187             return false;
   13188     }
   13189     if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, target))
   13190         return false;
   13191 
   13192     return true;
   13193 }
   13194 
   13195 // Dispatches to either BXWritePC or BranchWritePC based on architecture versions.
   13196 bool
   13197 EmulateInstructionARM::LoadWritePC (Context &context, uint32_t addr)
   13198 {
   13199     if (ArchVersion() >= ARMv5T)
   13200         return BXWritePC(context, addr);
   13201     else
   13202         return BranchWritePC((const Context)context, addr);
   13203 }
   13204 
   13205 // Dispatches to either BXWritePC or BranchWritePC based on architecture versions and current instruction set.
   13206 bool
   13207 EmulateInstructionARM::ALUWritePC (Context &context, uint32_t addr)
   13208 {
   13209     if (ArchVersion() >= ARMv7 && CurrentInstrSet() == eModeARM)
   13210         return BXWritePC(context, addr);
   13211     else
   13212         return BranchWritePC((const Context)context, addr);
   13213 }
   13214 
   13215 EmulateInstructionARM::Mode
   13216 EmulateInstructionARM::CurrentInstrSet ()
   13217 {
   13218     return m_opcode_mode;
   13219 }
   13220 
   13221 // Set the 'T' bit of our CPSR.  The m_opcode_mode gets updated when the next
   13222 // ReadInstruction() is performed.  This function has a side effect of updating
   13223 // the m_new_inst_cpsr member variable if necessary.
   13224 bool
   13225 EmulateInstructionARM::SelectInstrSet (Mode arm_or_thumb)
   13226 {
   13227     m_new_inst_cpsr = m_opcode_cpsr;
   13228     switch (arm_or_thumb)
   13229     {
   13230     default:
   13231         return false;
   13232     case eModeARM:
   13233         // Clear the T bit.
   13234         m_new_inst_cpsr &= ~MASK_CPSR_T;
   13235         break;
   13236     case eModeThumb:
   13237         // Set the T bit.
   13238         m_new_inst_cpsr |= MASK_CPSR_T;
   13239         break;
   13240     }
   13241     return true;
   13242 }
   13243 
   13244 // This function returns TRUE if the processor currently provides support for
   13245 // unaligned memory accesses, or FALSE otherwise. This is always TRUE in ARMv7,
   13246 // controllable by the SCTLR.U bit in ARMv6, and always FALSE before ARMv6.
   13247 bool
   13248 EmulateInstructionARM::UnalignedSupport()
   13249 {
   13250     return (ArchVersion() >= ARMv7);
   13251 }
   13252 
   13253 // The main addition and subtraction instructions can produce status information
   13254 // about both unsigned carry and signed overflow conditions.  This status
   13255 // information can be used to synthesize multi-word additions and subtractions.
   13256 EmulateInstructionARM::AddWithCarryResult
   13257 EmulateInstructionARM::AddWithCarry (uint32_t x, uint32_t y, uint8_t carry_in)
   13258 {
   13259     uint32_t result;
   13260     uint8_t carry_out;
   13261     uint8_t overflow;
   13262 
   13263     uint64_t unsigned_sum = x + y + carry_in;
   13264     int64_t signed_sum = (int32_t)x + (int32_t)y + (int32_t)carry_in;
   13265 
   13266     result = UnsignedBits(unsigned_sum, 31, 0);
   13267 //    carry_out = (result == unsigned_sum ? 0 : 1);
   13268     overflow = ((int32_t)result == signed_sum ? 0 : 1);
   13269 
   13270     if (carry_in)
   13271         carry_out = ((int32_t) x >= (int32_t) (~y)) ? 1 : 0;
   13272     else
   13273         carry_out = ((int32_t) x > (int32_t) y) ? 1 : 0;
   13274 
   13275     AddWithCarryResult res = { result, carry_out, overflow };
   13276     return res;
   13277 }
   13278 
   13279 uint32_t
   13280 EmulateInstructionARM::ReadCoreReg(uint32_t num, bool *success)
   13281 {
   13282     uint32_t reg_kind, reg_num;
   13283     switch (num)
   13284     {
   13285     case SP_REG:
   13286         reg_kind = eRegisterKindGeneric;
   13287         reg_num  = LLDB_REGNUM_GENERIC_SP;
   13288         break;
   13289     case LR_REG:
   13290         reg_kind = eRegisterKindGeneric;
   13291         reg_num  = LLDB_REGNUM_GENERIC_RA;
   13292         break;
   13293     case PC_REG:
   13294         reg_kind = eRegisterKindGeneric;
   13295         reg_num  = LLDB_REGNUM_GENERIC_PC;
   13296         break;
   13297     default:
   13298         if (num < SP_REG)
   13299         {
   13300             reg_kind = eRegisterKindDWARF;
   13301             reg_num  = dwarf_r0 + num;
   13302         }
   13303         else
   13304         {
   13305             //assert(0 && "Invalid register number");
   13306             *success = false;
   13307             return UINT32_MAX;
   13308         }
   13309         break;
   13310     }
   13311 
   13312     // Read our register.
   13313     uint32_t val = ReadRegisterUnsigned (reg_kind, reg_num, 0, success);
   13314 
   13315     // When executing an ARM instruction , PC reads as the address of the current
   13316     // instruction plus 8.
   13317     // When executing a Thumb instruction , PC reads as the address of the current
   13318     // instruction plus 4.
   13319     if (num == 15)
   13320     {
   13321         if (CurrentInstrSet() == eModeARM)
   13322             val += 8;
   13323         else
   13324             val += 4;
   13325     }
   13326 
   13327     return val;
   13328 }
   13329 
   13330 // Write the result to the ARM core register Rd, and optionally update the
   13331 // condition flags based on the result.
   13332 //
   13333 // This helper method tries to encapsulate the following pseudocode from the
   13334 // ARM Architecture Reference Manual:
   13335 //
   13336 // if d == 15 then         // Can only occur for encoding A1
   13337 //     ALUWritePC(result); // setflags is always FALSE here
   13338 // else
   13339 //     R[d] = result;
   13340 //     if setflags then
   13341 //         APSR.N = result<31>;
   13342 //         APSR.Z = IsZeroBit(result);
   13343 //         APSR.C = carry;
   13344 //         // APSR.V unchanged
   13345 //
   13346 // In the above case, the API client does not pass in the overflow arg, which
   13347 // defaults to ~0u.
   13348 bool
   13349 EmulateInstructionARM::WriteCoreRegOptionalFlags (Context &context,
   13350                                                   const uint32_t result,
   13351                                                   const uint32_t Rd,
   13352                                                   bool setflags,
   13353                                                   const uint32_t carry,
   13354                                                   const uint32_t overflow)
   13355 {
   13356     if (Rd == 15)
   13357     {
   13358         if (!ALUWritePC (context, result))
   13359             return false;
   13360     }
   13361     else
   13362     {
   13363         uint32_t reg_kind, reg_num;
   13364         switch (Rd)
   13365         {
   13366         case SP_REG:
   13367             reg_kind = eRegisterKindGeneric;
   13368             reg_num  = LLDB_REGNUM_GENERIC_SP;
   13369             break;
   13370         case LR_REG:
   13371             reg_kind = eRegisterKindGeneric;
   13372             reg_num  = LLDB_REGNUM_GENERIC_RA;
   13373             break;
   13374         default:
   13375             reg_kind = eRegisterKindDWARF;
   13376             reg_num  = dwarf_r0 + Rd;
   13377         }
   13378         if (!WriteRegisterUnsigned (context, reg_kind, reg_num, result))
   13379             return false;
   13380         if (setflags)
   13381             return WriteFlags (context, result, carry, overflow);
   13382     }
   13383     return true;
   13384 }
   13385 
   13386 // This helper method tries to encapsulate the following pseudocode from the
   13387 // ARM Architecture Reference Manual:
   13388 //
   13389 // APSR.N = result<31>;
   13390 // APSR.Z = IsZeroBit(result);
   13391 // APSR.C = carry;
   13392 // APSR.V = overflow
   13393 //
   13394 // Default arguments can be specified for carry and overflow parameters, which means
   13395 // not to update the respective flags.
   13396 bool
   13397 EmulateInstructionARM::WriteFlags (Context &context,
   13398                                    const uint32_t result,
   13399                                    const uint32_t carry,
   13400                                    const uint32_t overflow)
   13401 {
   13402     m_new_inst_cpsr = m_opcode_cpsr;
   13403     SetBit32(m_new_inst_cpsr, CPSR_N_POS, Bit32(result, CPSR_N_POS));
   13404     SetBit32(m_new_inst_cpsr, CPSR_Z_POS, result == 0 ? 1 : 0);
   13405     if (carry != ~0u)
   13406         SetBit32(m_new_inst_cpsr, CPSR_C_POS, carry);
   13407     if (overflow != ~0u)
   13408         SetBit32(m_new_inst_cpsr, CPSR_V_POS, overflow);
   13409     if (m_new_inst_cpsr != m_opcode_cpsr)
   13410     {
   13411         if (!WriteRegisterUnsigned (context, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FLAGS, m_new_inst_cpsr))
   13412             return false;
   13413     }
   13414     return true;
   13415 }
   13416 
   13417 bool
   13418 EmulateInstructionARM::EvaluateInstruction (uint32_t evaluate_options)
   13419 {
   13420     // Advance the ITSTATE bits to their values for the next instruction.
   13421     if (m_opcode_mode == eModeThumb && m_it_session.InITBlock())
   13422         m_it_session.ITAdvance();
   13423 
   13424     ARMOpcode *opcode_data = NULL;
   13425 
   13426     if (m_opcode_mode == eModeThumb)
   13427         opcode_data = GetThumbOpcodeForInstruction (m_opcode.GetOpcode32(), m_arm_isa);
   13428     else if (m_opcode_mode == eModeARM)
   13429         opcode_data = GetARMOpcodeForInstruction (m_opcode.GetOpcode32(), m_arm_isa);
   13430 
   13431     if (opcode_data == NULL)
   13432         return false;
   13433 
   13434     const bool auto_advance_pc = evaluate_options & eEmulateInstructionOptionAutoAdvancePC;
   13435     m_ignore_conditions = evaluate_options & eEmulateInstructionOptionIgnoreConditions;
   13436 
   13437     bool success = false;
   13438     if (m_opcode_cpsr == 0 || m_ignore_conditions == false)
   13439     {
   13440         m_opcode_cpsr = ReadRegisterUnsigned (eRegisterKindDWARF,
   13441                                                 dwarf_cpsr,
   13442                                                 0,
   13443                                                 &success);
   13444     }
   13445 
   13446     // Only return false if we are unable to read the CPSR if we care about conditions
   13447     if (success == false && m_ignore_conditions == false)
   13448         return false;
   13449 
   13450     uint32_t orig_pc_value = 0;
   13451     if (auto_advance_pc)
   13452     {
   13453         orig_pc_value = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_pc, 0, &success);
   13454         if (!success)
   13455             return false;
   13456     }
   13457 
   13458     // Call the Emulate... function.
   13459     success = (this->*opcode_data->callback) (m_opcode.GetOpcode32(), opcode_data->encoding);
   13460     if (!success)
   13461         return false;
   13462 
   13463     if (auto_advance_pc)
   13464     {
   13465         uint32_t after_pc_value = ReadRegisterUnsigned (eRegisterKindDWARF, dwarf_pc, 0, &success);
   13466         if (!success)
   13467             return false;
   13468 
   13469         if (auto_advance_pc && (after_pc_value == orig_pc_value))
   13470         {
   13471             if (opcode_data->size == eSize32)
   13472                 after_pc_value += 4;
   13473             else if (opcode_data->size == eSize16)
   13474                 after_pc_value += 2;
   13475 
   13476             EmulateInstruction::Context context;
   13477             context.type = eContextAdvancePC;
   13478             context.SetNoArgs();
   13479             if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_pc, after_pc_value))
   13480                 return false;
   13481 
   13482         }
   13483     }
   13484     return true;
   13485 }
   13486 
   13487 bool
   13488 EmulateInstructionARM::TestEmulation (Stream *out_stream, ArchSpec &arch, OptionValueDictionary *test_data)
   13489 {
   13490     if (!test_data)
   13491     {
   13492         out_stream->Printf ("TestEmulation: Missing test data.\n");
   13493         return false;
   13494     }
   13495 
   13496     static ConstString opcode_key ("opcode");
   13497     static ConstString before_key ("before_state");
   13498     static ConstString after_key ("after_state");
   13499 
   13500     OptionValueSP value_sp = test_data->GetValueForKey (opcode_key);
   13501 
   13502     uint32_t test_opcode;
   13503     if ((value_sp.get() == NULL) || (value_sp->GetType() != OptionValue::eTypeUInt64))
   13504     {
   13505         out_stream->Printf ("TestEmulation: Error reading opcode from test file.\n");
   13506         return false;
   13507     }
   13508     test_opcode = value_sp->GetUInt64Value ();
   13509 
   13510     if (arch.GetTriple().getArch() == llvm::Triple::arm)
   13511     {
   13512         m_opcode_mode = eModeARM;
   13513         m_opcode.SetOpcode32 (test_opcode);
   13514     }
   13515     else if (arch.GetTriple().getArch() == llvm::Triple::thumb)
   13516     {
   13517         m_opcode_mode = eModeThumb;
   13518         if (test_opcode < 0x10000)
   13519             m_opcode.SetOpcode16 (test_opcode);
   13520         else
   13521             m_opcode.SetOpcode32 (test_opcode);
   13522 
   13523     }
   13524     else
   13525     {
   13526         out_stream->Printf ("TestEmulation:  Invalid arch.\n");
   13527         return false;
   13528     }
   13529 
   13530     EmulationStateARM before_state;
   13531     EmulationStateARM after_state;
   13532 
   13533     value_sp = test_data->GetValueForKey (before_key);
   13534     if ((value_sp.get() == NULL) || (value_sp->GetType() != OptionValue::eTypeDictionary))
   13535     {
   13536         out_stream->Printf ("TestEmulation:  Failed to find 'before' state.\n");
   13537         return false;
   13538     }
   13539 
   13540     OptionValueDictionary *state_dictionary = value_sp->GetAsDictionary ();
   13541     if (!before_state.LoadStateFromDictionary (state_dictionary))
   13542     {
   13543         out_stream->Printf ("TestEmulation:  Failed loading 'before' state.\n");
   13544         return false;
   13545     }
   13546 
   13547     value_sp = test_data->GetValueForKey (after_key);
   13548     if ((value_sp.get() == NULL) || (value_sp->GetType() != OptionValue::eTypeDictionary))
   13549     {
   13550         out_stream->Printf ("TestEmulation:  Failed to find 'after' state.\n");
   13551         return false;
   13552     }
   13553 
   13554     state_dictionary = value_sp->GetAsDictionary ();
   13555     if (!after_state.LoadStateFromDictionary (state_dictionary))
   13556     {
   13557         out_stream->Printf ("TestEmulation: Failed loading 'after' state.\n");
   13558         return false;
   13559     }
   13560 
   13561     SetBaton ((void *) &before_state);
   13562     SetCallbacks (&EmulationStateARM::ReadPseudoMemory,
   13563                   &EmulationStateARM::WritePseudoMemory,
   13564                   &EmulationStateARM::ReadPseudoRegister,
   13565                   &EmulationStateARM::WritePseudoRegister);
   13566 
   13567     bool success = EvaluateInstruction (eEmulateInstructionOptionAutoAdvancePC);
   13568     if (!success)
   13569     {
   13570         out_stream->Printf ("TestEmulation:  EvaluateInstruction() failed.\n");
   13571         return false;
   13572     }
   13573 
   13574     success = before_state.CompareState (after_state);
   13575     if (!success)
   13576         out_stream->Printf ("TestEmulation:  'before' and 'after' states do not match.\n");
   13577 
   13578     return success;
   13579 }
   13580 //
   13581 //
   13582 //const char *
   13583 //EmulateInstructionARM::GetRegisterName (uint32_t reg_kind, uint32_t reg_num)
   13584 //{
   13585 //    if (reg_kind == eRegisterKindGeneric)
   13586 //    {
   13587 //        switch (reg_num)
   13588 //        {
   13589 //        case LLDB_REGNUM_GENERIC_PC:    return "pc";
   13590 //        case LLDB_REGNUM_GENERIC_SP:    return "sp";
   13591 //        case LLDB_REGNUM_GENERIC_FP:    return "fp";
   13592 //        case LLDB_REGNUM_GENERIC_RA:    return "lr";
   13593 //        case LLDB_REGNUM_GENERIC_FLAGS: return "cpsr";
   13594 //        default: return NULL;
   13595 //        }
   13596 //    }
   13597 //    else if (reg_kind == eRegisterKindDWARF)
   13598 //    {
   13599 //        return GetARMDWARFRegisterName (reg_num);
   13600 //    }
   13601 //    return NULL;
   13602 //}
   13603 //
   13604 bool
   13605 EmulateInstructionARM::CreateFunctionEntryUnwind (UnwindPlan &unwind_plan)
   13606 {
   13607     unwind_plan.Clear();
   13608     unwind_plan.SetRegisterKind (eRegisterKindDWARF);
   13609 
   13610     UnwindPlan::RowSP row(new UnwindPlan::Row);
   13611 
   13612     // Our previous Call Frame Address is the stack pointer
   13613     row->SetCFARegister (dwarf_sp);
   13614 
   13615     // Our previous PC is in the LR
   13616     row->SetRegisterLocationToRegister(dwarf_pc, dwarf_lr, true);
   13617     unwind_plan.AppendRow (row);
   13618 
   13619     // All other registers are the same.
   13620 
   13621     unwind_plan.SetSourceName ("EmulateInstructionARM");
   13622     unwind_plan.SetSourcedFromCompiler (eLazyBoolNo);
   13623     unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolYes);
   13624     return true;
   13625 }
   13626