diff options
Diffstat (limited to 'source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp')
-rw-r--r-- | source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp | 406 |
1 files changed, 205 insertions, 201 deletions
diff --git a/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp b/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp index 95ae549e0e4b..d646d4d4754a 100644 --- a/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp +++ b/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp @@ -290,9 +290,8 @@ EmulateInstructionARM::GetRegisterInfo (lldb::RegisterKind reg_kind, uint32_t re uint32_t EmulateInstructionARM::GetFramePointerRegisterNumber () const { - if (m_arch.GetTriple().getEnvironment() == llvm::Triple::Android) + if (m_arch.GetTriple().isAndroid()) return LLDB_INVALID_REGNUM; // Don't use frame pointer on android - bool is_apple = false; if (m_arch.GetTriple().getVendor() == llvm::Triple::Apple) is_apple = true; @@ -301,6 +300,8 @@ EmulateInstructionARM::GetFramePointerRegisterNumber () const case llvm::Triple::Darwin: case llvm::Triple::MacOSX: case llvm::Triple::IOS: + case llvm::Triple::TvOS: + case llvm::Triple::WatchOS: is_apple = true; break; default: @@ -387,9 +388,8 @@ EmulateInstructionARM::EmulatePUSH (const uint32_t opcode, const ARMEncoding enc } #endif - bool conditional = false; bool success = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { const uint32_t addr_byte_size = GetAddressByteSize(); const addr_t sp = ReadCoreReg (SP_REG, &success); @@ -442,10 +442,7 @@ EmulateInstructionARM::EmulatePUSH (const uint32_t opcode, const ARMEncoding enc uint32_t i; EmulateInstruction::Context context; - if (conditional) - context.type = EmulateInstruction::eContextRegisterStore; - else - context.type = EmulateInstruction::eContextPushRegisterOnStack; + context.type = EmulateInstruction::eContextPushRegisterOnStack; RegisterInfo reg_info; RegisterInfo sp_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg); @@ -511,8 +508,7 @@ EmulateInstructionARM::EmulatePOP (const uint32_t opcode, const ARMEncoding enco bool success = false; - bool conditional = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { const uint32_t addr_byte_size = GetAddressByteSize(); const addr_t sp = ReadCoreReg (SP_REG, &success); @@ -574,10 +570,7 @@ EmulateInstructionARM::EmulatePOP (const uint32_t opcode, const ARMEncoding enco uint32_t i, data; EmulateInstruction::Context context; - if (conditional) - context.type = EmulateInstruction::eContextRegisterLoad; - else - context.type = EmulateInstruction::eContextPopRegisterOffStack; + context.type = EmulateInstruction::eContextPopRegisterOffStack; RegisterInfo sp_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg); @@ -586,7 +579,7 @@ EmulateInstructionARM::EmulatePOP (const uint32_t opcode, const ARMEncoding enco { if (BitIsSet (registers, i)) { - context.SetRegisterPlusOffset (sp_reg, addr - sp); + context.SetAddress(addr); data = MemARead(context, addr, 4, 0, &success); if (!success) return false; @@ -900,12 +893,12 @@ EmulateInstructionARM::EmulateMOVRdImm (const uint32_t opcode, const ARMEncoding break; case eEncodingA1: - // d = UInt(Rd); setflags = (S == Ô1Õ); (imm32, carry) = ARMExpandImm_C(imm12, APSR.C); + // d = UInt(Rd); setflags = (S == '1'); (imm32, carry) = ARMExpandImm_C(imm12, APSR.C); Rd = Bits32 (opcode, 15, 12); setflags = BitIsSet (opcode, 20); imm32 = ARMExpandImm_C (opcode, APSR_C, carry); - // if Rd == Ô1111Õ && S == Ô1Õ then SEE SUBS PC, LR and related instructions; + // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions; if ((Rd == 15) && setflags) return EmulateSUBSPcLrEtc (opcode, encoding); @@ -1971,9 +1964,8 @@ EmulateInstructionARM::EmulateSTRRtSP (const uint32_t opcode, const ARMEncoding } #endif - bool conditional = false; bool success = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { const uint32_t addr_byte_size = GetAddressByteSize(); const addr_t sp = ReadCoreReg (SP_REG, &success); @@ -2018,10 +2010,7 @@ EmulateInstructionARM::EmulateSTRRtSP (const uint32_t opcode, const ARMEncoding addr = sp; EmulateInstruction::Context context; - if (conditional) - context.type = EmulateInstruction::eContextRegisterStore; - else - context.type = EmulateInstruction::eContextPushRegisterOnStack; + context.type = EmulateInstruction::eContextPushRegisterOnStack; RegisterInfo sp_reg; RegisterInfo dwarf_reg; @@ -2082,8 +2071,7 @@ EmulateInstructionARM::EmulateVPUSH (const uint32_t opcode, const ARMEncoding en #endif bool success = false; - bool conditional = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { const uint32_t addr_byte_size = GetAddressByteSize(); const addr_t sp = ReadCoreReg (SP_REG, &success); @@ -2125,10 +2113,8 @@ EmulateInstructionARM::EmulateVPUSH (const uint32_t opcode, const ARMEncoding en uint32_t i; EmulateInstruction::Context context; - if (conditional) - context.type = EmulateInstruction::eContextRegisterStore; - else - context.type = EmulateInstruction::eContextPushRegisterOnStack; + context.type = EmulateInstruction::eContextPushRegisterOnStack; + RegisterInfo dwarf_reg; RegisterInfo sp_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg); @@ -2178,8 +2164,7 @@ EmulateInstructionARM::EmulateVPOP (const uint32_t opcode, const ARMEncoding enc #endif bool success = false; - bool conditional = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { const uint32_t addr_byte_size = GetAddressByteSize(); const addr_t sp = ReadCoreReg (SP_REG, &success); @@ -2222,17 +2207,15 @@ EmulateInstructionARM::EmulateVPOP (const uint32_t opcode, const ARMEncoding enc uint64_t data; // uint64_t to accommodate 64-bit registers. EmulateInstruction::Context context; - if (conditional) - context.type = EmulateInstruction::eContextRegisterLoad; - else - context.type = EmulateInstruction::eContextPopRegisterOffStack; + context.type = EmulateInstruction::eContextPopRegisterOffStack; + RegisterInfo dwarf_reg; RegisterInfo sp_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg); for (i=0; i<regs; ++i) { GetRegisterInfo (eRegisterKindDWARF, start_reg + d + i, dwarf_reg); - context.SetRegisterPlusOffset (sp_reg, addr - sp); + context.SetAddress(addr); data = MemARead(context, addr, reg_byte_size, 0, &success); if (!success) return false; @@ -3462,8 +3445,7 @@ EmulateInstructionARM::EmulateLDM (const uint32_t opcode, const ARMEncoding enco #endif bool success = false; - bool conditional = false; - if (ConditionPassed(opcode, &conditional)) + if (ConditionPassed(opcode)) { uint32_t n; uint32_t registers = 0; @@ -3536,10 +3518,8 @@ EmulateInstructionARM::EmulateLDM (const uint32_t opcode, const ARMEncoding enco context.SetRegisterPlusOffset (dwarf_reg, offset); if (wback && (n == 13)) // Pop Instruction { - if (conditional) - context.type = EmulateInstruction::eContextRegisterLoad; - else - context.type = EmulateInstruction::eContextPopRegisterOffStack; + context.type = EmulateInstruction::eContextPopRegisterOffStack; + context.SetAddress(base_address + offset); } // R[i] = MemA [address, 4]; address = address + 4; @@ -4459,7 +4439,7 @@ EmulateInstructionARM::EmulateSTMDB (const uint32_t opcode, const ARMEncoding en break; case eEncodingA1: - // if W == '1' && Rn == '1101Õ && BitCount(register_list) >= 2 then SEE PUSH; + // if W == '1' && Rn == '1101' && BitCount(register_list) >= 2 then SEE PUSH; if (BitIsSet (opcode, 21) && (Bits32 (opcode, 19, 16) == 13) && BitCount (Bits32 (opcode, 15, 0)) >= 2) { // See Push @@ -4801,7 +4781,11 @@ EmulateInstructionARM::EmulateSTRThumb (const uint32_t opcode, const ARMEncoding address = base_address; EmulateInstruction::Context context; - context.type = eContextRegisterStore; + if (n == 13) + context.type = eContextPushRegisterOnStack; + else + context.type = eContextRegisterStore; + RegisterInfo base_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg); @@ -4829,8 +4813,12 @@ EmulateInstructionARM::EmulateSTRThumb (const uint32_t opcode, const ARMEncoding // if wback then R[n] = offset_addr; if (wback) { - context.type = eContextRegisterLoad; + if (n == 13) + context.type = eContextAdjustStackPointer; + else + context.type = eContextAdjustBaseRegister; context.SetAddress (offset_addr); + if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr)) return false; } @@ -9579,7 +9567,7 @@ EmulateInstructionARM::EmulateSUBSPReg (const uint32_t opcode, const ARMEncoding if ConditionPassed() then EncodingSpecificOperations(); shifted = Shift(R[m], shift_t, shift_n, APSR.C); - (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), Ô1Õ); + (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), '1'); if d == 15 then // Can only occur for ARM encoding ALUWritePC(result); // setflags is always FALSE here else @@ -9604,7 +9592,7 @@ EmulateInstructionARM::EmulateSUBSPReg (const uint32_t opcode, const ARMEncoding switch (encoding) { case eEncodingT1: - // d = UInt(Rd); m = UInt(Rm); setflags = (S == Ô1Õ); + // d = UInt(Rd); m = UInt(Rm); setflags = (S == '1'); d = Bits32 (opcode, 11, 8); m = Bits32 (opcode, 3, 0); setflags = BitIsSet (opcode, 20); @@ -9622,12 +9610,12 @@ EmulateInstructionARM::EmulateSUBSPReg (const uint32_t opcode, const ARMEncoding break; case eEncodingA1: - // d = UInt(Rd); m = UInt(Rm); setflags = (S == Ô1Õ); + // d = UInt(Rd); m = UInt(Rm); setflags = (S == '1'); d = Bits32 (opcode, 15, 12); m = Bits32 (opcode, 3, 0); setflags = BitIsSet (opcode, 20); - // if Rd == Ô1111Õ && S == Ô1Õ then SEE SUBS PC, LR and related instructions; + // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions; if (d == 15 && setflags) EmulateSUBSPcLrEtc (opcode, encoding); @@ -9648,7 +9636,7 @@ EmulateInstructionARM::EmulateSUBSPReg (const uint32_t opcode, const ARMEncoding if (!success) return false; - // (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), Ô1Õ); + // (result, carry, overflow) = AddWithCarry(SP, NOT(shifted), '1'); uint32_t sp_val = ReadCoreReg (SP_REG, &success); if (!success) return false; @@ -9679,7 +9667,7 @@ EmulateInstructionARM::EmulateADDRegShift (const uint32_t opcode, const ARMEncod EncodingSpecificOperations(); shift_n = UInt(R[s]<7:0>); shifted = Shift(R[m], shift_t, shift_n, APSR.C); - (result, carry, overflow) = AddWithCarry(R[n], shifted, Ô0Õ); + (result, carry, overflow) = AddWithCarry(R[n], shifted, '0'); R[d] = result; if setflags then APSR.N = result<31>; @@ -9708,7 +9696,7 @@ EmulateInstructionARM::EmulateADDRegShift (const uint32_t opcode, const ARMEncod m = Bits32 (opcode, 3, 0); s = Bits32 (opcode, 11, 8); - // setflags = (S == Ô1Õ); shift_t = DecodeRegShift(type); + // setflags = (S == '1'); shift_t = DecodeRegShift(type); setflags = BitIsSet (opcode, 20); shift_t = DecodeRegShift (Bits32 (opcode, 6, 5)); @@ -9737,7 +9725,7 @@ EmulateInstructionARM::EmulateADDRegShift (const uint32_t opcode, const ARMEncod if (!success) return false; - // (result, carry, overflow) = AddWithCarry(R[n], shifted, Ô0Õ); + // (result, carry, overflow) = AddWithCarry(R[n], shifted, '0'); uint32_t Rn = ReadCoreReg (n, &success); if (!success) return false; @@ -9776,7 +9764,7 @@ EmulateInstructionARM::EmulateSUBReg (const uint32_t opcode, const ARMEncoding e if ConditionPassed() then EncodingSpecificOperations(); shifted = Shift(R[m], shift_t, shift_n, APSR.C); - (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), Ô1Õ); + (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), '1'); if d == 15 then // Can only occur for ARM encoding ALUWritePC(result); // setflags is always FALSE here else @@ -9839,14 +9827,14 @@ EmulateInstructionARM::EmulateSUBReg (const uint32_t opcode, const ARMEncoding e break; case eEncodingA1: - // if Rn == Ô1101Õ then SEE SUB (SP minus register); - // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = (S == Ô1Õ); + // if Rn == '1101' then SEE SUB (SP minus register); + // d = UInt(Rd); n = UInt(Rn); m = UInt(Rm); setflags = (S == '1'); d = Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); m = Bits32 (opcode, 3, 0); setflags = BitIsSet (opcode, 20); - // if Rd == Ô1111Õ && S == Ô1Õ then SEE SUBS PC, LR and related instructions; + // if Rd == '1111' && S == '1' then SEE SUBS PC, LR and related instructions; if ((d == 15) && setflags) EmulateSUBSPcLrEtc (opcode, encoding); @@ -9868,7 +9856,7 @@ EmulateInstructionARM::EmulateSUBReg (const uint32_t opcode, const ARMEncoding e if (!success) return false; - // (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), Ô1Õ); + // (result, carry, overflow) = AddWithCarry(R[n], NOT(shifted), '1'); uint32_t Rn = ReadCoreReg (n, &success); if (!success) return false; @@ -9929,7 +9917,7 @@ EmulateInstructionARM::EmulateSTREX (const uint32_t opcode, const ARMEncoding en switch (encoding) { case eEncodingT1: - // d = UInt(Rd); t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // d = UInt(Rd); t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm8:'00', 32); d = Bits32 (opcode, 11, 8); t = Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); @@ -10037,13 +10025,13 @@ EmulateInstructionARM::EmulateSTRBImmARM (const uint32_t opcode, const ARMEncodi switch (encoding) { case eEncodingA1: - // if P == Ô0Õ && W == Ô1Õ then SEE STRBT; + // if P == '0' && W == '1' then SEE STRBT; // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32); t = Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 11, 0); - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); @@ -10135,14 +10123,14 @@ EmulateInstructionARM::EmulateSTRImmARM (const uint32_t opcode, const ARMEncodin switch (encoding) { case eEncodingA1: - // if P == Ô0Õ && W == Ô1Õ then SEE STRT; - // if Rn == Ô1101Õ && P == Ô1Õ && U == Ô0Õ && W == Ô1Õ && imm12 == Ô000000000100Õ then SEE PUSH; + // if P == '0' && W == '1' then SEE STRT; + // if Rn == '1101' && P == '1' && U == '0' && W == '1' && imm12 == '000000000100' then SEE PUSH; // t = UInt(Rt); n = UInt(Rn); imm32 = ZeroExtend(imm12, 32); t = Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 11, 0); - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); @@ -10247,15 +10235,15 @@ EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEnc switch (encoding) { case eEncodingT1: - //if P == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - //if Rn == Ô1111Õ then SEE LDRD (literal); - //t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + //if P == '0' && W == '0' then SEE 'Related encodings'; + //if Rn == '1111' then SEE LDRD (literal); + //t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:'00', 32); t = Bits32 (opcode, 15, 12); t2 = Bits32 (opcode, 11, 8); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 7, 0) << 2; - //index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (W == Ô1Õ); + //index = (P == '1'); add = (U == '1'); wback = (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); @@ -10271,8 +10259,8 @@ EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEnc break; case eEncodingA1: - //if Rn == Ô1111Õ then SEE LDRD (literal); - //if Rt<0> == Ô1Õ then UNPREDICTABLE; + //if Rn == '1111' then SEE LDRD (literal); + //if Rt<0> == '1' then UNPREDICTABLE; //t = UInt(Rt); t2 = t+1; n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32); t = Bits32 (opcode, 15, 12); if (BitIsSet (t, 0)) @@ -10281,12 +10269,12 @@ EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEnc n = Bits32 (opcode, 19, 16); imm32 = (Bits32 (opcode, 11, 8) << 4) | Bits32 (opcode, 3, 0); - //index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + //index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); - //if P == Ô0Õ && W == Ô1Õ then UNPREDICTABLE; + //if P == '0' && W == '1' then UNPREDICTABLE; if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21)) return false; @@ -10327,8 +10315,11 @@ EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEnc GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + n, base_reg); EmulateInstruction::Context context; - context.type = eContextRegisterLoad; - context.SetRegisterPlusOffset (base_reg, address - Rn); + if (n == 13) + context.type = eContextPopRegisterOffStack; + else + context.type = eContextRegisterLoad; + context.SetAddress(address); const uint32_t addr_byte_size = GetAddressByteSize(); uint32_t data = MemARead (context, address, addr_byte_size, 0, &success); @@ -10339,8 +10330,7 @@ EmulateInstructionARM::EmulateLDRDImmediate (const uint32_t opcode, const ARMEnc return false; //R[t2] = MemA[address+4,4]; - - context.SetRegisterPlusOffset (base_reg, (address + 4) - Rn); + context.SetAddress(address + 4); data = MemARead (context, address + 4, addr_byte_size, 0, &success); if (!success) return false; @@ -10392,7 +10382,7 @@ EmulateInstructionARM::EmulateLDRDRegister (const uint32_t opcode, const ARMEnco switch (encoding) { case eEncodingA1: - // if Rt<0> == Ô1Õ then UNPREDICTABLE; + // if Rt<0> == '1' then UNPREDICTABLE; // t = UInt(Rt); t2 = t+1; n = UInt(Rn); m = UInt(Rm); t = Bits32 (opcode, 15, 12); if (BitIsSet (t, 0)) @@ -10401,12 +10391,12 @@ EmulateInstructionARM::EmulateLDRDRegister (const uint32_t opcode, const ARMEnco n = Bits32 (opcode, 19, 16); m = Bits32 (opcode, 3, 0); - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); - // if P == Ô0Õ && W == Ô1Õ then UNPREDICTABLE; + // if P == '0' && W == '1' then UNPREDICTABLE; if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21)) return false; @@ -10454,8 +10444,11 @@ EmulateInstructionARM::EmulateLDRDRegister (const uint32_t opcode, const ARMEnco address = Rn; EmulateInstruction::Context context; - context.type = eContextRegisterLoad; - context.SetRegisterPlusIndirectOffset (base_reg, offset_reg); + if (n == 13) + context.type = eContextPopRegisterOffStack; + else + context.type = eContextRegisterLoad; + context.SetAddress(address); // R[t] = MemA[address,4]; const uint32_t addr_byte_size = GetAddressByteSize(); @@ -10519,14 +10512,14 @@ EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding switch (encoding) { case eEncodingT1: - // if P == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - // t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // if P == '0' && W == '0' then SEE 'Related encodings'; + // t = UInt(Rt); t2 = UInt(Rt2); n = UInt(Rn); imm32 = ZeroExtend(imm8:'00', 32); t = Bits32 (opcode, 15, 12); t2 = Bits32 (opcode, 11, 8); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 7, 0) << 2; - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); @@ -10542,7 +10535,7 @@ EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding break; case eEncodingA1: - // if Rt<0> == Ô1Õ then UNPREDICTABLE; + // if Rt<0> == '1' then UNPREDICTABLE; // t = UInt(Rt); t2 = t+1; n = UInt(Rn); imm32 = ZeroExtend(imm4H:imm4L, 32); t = Bits32 (opcode, 15, 12); if (BitIsSet (t, 0)) @@ -10552,12 +10545,12 @@ EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding n = Bits32 (opcode, 19, 16); imm32 = (Bits32 (opcode, 11, 8) << 4) | Bits32 (opcode, 3, 0); - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); - // if P == Ô0Õ && W == Ô1Õ then UNPREDICTABLE; + // if P == '0' && W == '1' then UNPREDICTABLE; if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21)) return false; @@ -10605,7 +10598,10 @@ EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding return false; EmulateInstruction::Context context; - context.type = eContextRegisterStore; + if (n == 13) + context.type = eContextPushRegisterOnStack; + else + context.type = eContextRegisterStore; context.SetRegisterToRegisterPlusOffset (data_reg, base_reg, address - Rn); const uint32_t addr_byte_size = GetAddressByteSize(); @@ -10627,9 +10623,12 @@ EmulateInstructionARM::EmulateSTRDImm (const uint32_t opcode, const ARMEncoding //if wback then R[n] = offset_addr; if (wback) { - context.type = eContextAdjustBaseRegister; + if (n == 13) + context.type = eContextAdjustStackPointer; + else + context.type = eContextAdjustBaseRegister; context.SetAddress (offset_addr); - + if (!WriteRegisterUnsigned (context, eRegisterKindDWARF, dwarf_r0 + n, offset_addr)) return false; } @@ -10667,7 +10666,7 @@ EmulateInstructionARM::EmulateSTRDReg (const uint32_t opcode, const ARMEncoding switch (encoding) { case eEncodingA1: - // if Rt<0> == Ô1Õ then UNPREDICTABLE; + // if Rt<0> == '1' then UNPREDICTABLE; // t = UInt(Rt); t2 = t+1; n = UInt(Rn); m = UInt(Rm); t = Bits32 (opcode, 15, 12); if (BitIsSet (t, 0)) @@ -10677,12 +10676,12 @@ EmulateInstructionARM::EmulateSTRDReg (const uint32_t opcode, const ARMEncoding n = Bits32 (opcode, 19, 16); m = Bits32 (opcode, 3, 0); - // index = (P == Ô1Õ); add = (U == Ô1Õ); wback = (P == Ô0Õ) || (W == Ô1Õ); + // index = (P == '1'); add = (U == '1'); wback = (P == '0') || (W == '1'); index = BitIsSet (opcode, 24); add = BitIsSet (opcode, 23); wback = BitIsClear (opcode, 24) || BitIsSet (opcode, 21); - // if P == Ô0Õ && W == Ô1Õ then UNPREDICTABLE; + // if P == '0' && W == '1' then UNPREDICTABLE; if (BitIsClear (opcode, 24) && BitIsSet (opcode, 21)) return false; @@ -10737,7 +10736,11 @@ EmulateInstructionARM::EmulateSTRDReg (const uint32_t opcode, const ARMEncoding return false; EmulateInstruction::Context context; - context.type = eContextRegisterStore; + if (t == 13) + context.type = eContextPushRegisterOnStack; + else + context.type = eContextRegisterStore; + GetRegisterInfo (eRegisterKindDWARF, dwarf_r0 + t, data_reg); context.SetRegisterToRegisterPlusIndirectOffset (base_reg, offset_reg, data_reg); @@ -10808,25 +10811,25 @@ EmulateInstructionARM::EmulateVLDM (const uint32_t opcode, const ARMEncoding enc { case eEncodingT1: case eEncodingA1: - // if P == Ô0Õ && U == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - // if P == Ô0Õ && U == Ô1Õ && W == Ô1Õ && Rn == Ô1101Õ then SEE VPOP; - // if P == Ô1Õ && W == Ô0Õ then SEE VLDR; - // if P == U && W == Ô1Õ then UNDEFINED; + // if P == '0' && U == '0' && W == '0' then SEE 'Related encodings'; + // if P == '0' && U == '1' && W == '1' && Rn == '1101' then SEE VPOP; + // if P == '1' && W == '0' then SEE VLDR; + // if P == U && W == '1' then UNDEFINED; if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21)) return false; // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !) - // single_regs = FALSE; add = (U == Ô1Õ); wback = (W == Ô1Õ); + // single_regs = FALSE; add = (U == '1'); wback = (W == '1'); single_regs = false; add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); - // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:'00', 32); d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 7, 0) << 2; - // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see ÒFLDMXÓ. + // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see 'FLDMX'. regs = Bits32 (opcode, 7, 0) / 2; // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE; @@ -10841,22 +10844,22 @@ EmulateInstructionARM::EmulateVLDM (const uint32_t opcode, const ARMEncoding enc case eEncodingT2: case eEncodingA2: - // if P == Ô0Õ && U == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - // if P == Ô0Õ && U == Ô1Õ && W == Ô1Õ && Rn == Ô1101Õ then SEE VPOP; - // if P == Ô1Õ && W == Ô0Õ then SEE VLDR; - // if P == U && W == Ô1Õ then UNDEFINED; + // if P == '0' && U == '0' && W == '0' then SEE 'Related encodings'; + // if P == '0' && U == '1' && W == '1' && Rn == '1101' then SEE VPOP; + // if P == '1' && W == '0' then SEE VLDR; + // if P == U && W == '1' then UNDEFINED; if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21)) return false; // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !) - // single_regs = TRUE; add = (U == Ô1Õ); wback = (W == Ô1Õ); d = UInt(Vd:D); n = UInt(Rn); + // single_regs = TRUE; add = (U == '1'); wback = (W == '1'); d = UInt(Vd:D); n = UInt(Rn); single_regs = true; add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22); n = Bits32 (opcode, 19, 16); - // imm32 = ZeroExtend(imm8:Õ00Õ, 32); regs = UInt(imm8); + // imm32 = ZeroExtend(imm8:'00', 32); regs = UInt(imm8); imm32 = Bits32 (opcode, 7, 0) << 2; regs = Bits32 (opcode, 7, 0); @@ -11000,25 +11003,25 @@ EmulateInstructionARM::EmulateVSTM (const uint32_t opcode, const ARMEncoding enc { case eEncodingT1: case eEncodingA1: - // if P == Ô0Õ && U == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - // if P == Ô1Õ && U == Ô0Õ && W == Ô1Õ && Rn == Ô1101Õ then SEE VPUSH; - // if P == Ô1Õ && W == Ô0Õ then SEE VSTR; - // if P == U && W == Ô1Õ then UNDEFINED; + // if P == '0' && U == '0' && W == '0' then SEE 'Related encodings'; + // if P == '1' && U == '0' && W == '1' && Rn == '1101' then SEE VPUSH; + // if P == '1' && W == '0' then SEE VSTR; + // if P == U && W == '1' then UNDEFINED; if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21)) return false; // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !) - // single_regs = FALSE; add = (U == Ô1Õ); wback = (W == Ô1Õ); + // single_regs = FALSE; add = (U == '1'); wback = (W == '1'); single_regs = false; add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); - // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // d = UInt(D:Vd); n = UInt(Rn); imm32 = ZeroExtend(imm8:'00', 32); d = (Bit32 (opcode, 22) << 4) | Bits32 (opcode, 15, 12); n = Bits32 (opcode, 19, 16); imm32 = Bits32 (opcode, 7, 0) << 2; - // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see ÒFSTMXÓ. + // regs = UInt(imm8) DIV 2; // If UInt(imm8) is odd, see 'FSTMX'. regs = Bits32 (opcode, 7, 0) / 2; // if n == 15 && (wback || CurrentInstrSet() != InstrSet_ARM) then UNPREDICTABLE; @@ -11033,22 +11036,22 @@ EmulateInstructionARM::EmulateVSTM (const uint32_t opcode, const ARMEncoding enc case eEncodingT2: case eEncodingA2: - // if P == Ô0Õ && U == Ô0Õ && W == Ô0Õ then SEE ÒRelated encodingsÓ; - // if P == Ô1Õ && U == Ô0Õ && W == Ô1Õ && Rn == Ô1101Õ then SEE VPUSH; - // if P == Ô1Õ && W == Ô0Õ then SEE VSTR; - // if P == U && W == Ô1Õ then UNDEFINED; + // if P == '0' && U == '0' && W == '0' then SEE 'Related encodings'; + // if P == '1' && U == '0' && W == '1' && Rn == '1101' then SEE VPUSH; + // if P == '1' && W == '0' then SEE VSTR; + // if P == U && W == '1' then UNDEFINED; if ((Bit32 (opcode, 24) == Bit32 (opcode, 23)) && BitIsSet (opcode, 21)) return false; // // Remaining combinations are PUW = 010 (IA without !), 011 (IA with !), 101 (DB with !) - // single_regs = TRUE; add = (U == Ô1Õ); wback = (W == Ô1Õ); d = UInt(Vd:D); n = UInt(Rn); + // single_regs = TRUE; add = (U == '1'); wback = (W == '1'); d = UInt(Vd:D); n = UInt(Rn); single_regs = true; add = BitIsSet (opcode, 23); wback = BitIsSet (opcode, 21); d = (Bits32 (opcode, 15, 12) << 1) | Bit32 (opcode, 22); n = Bits32 (opcode, 19, 16); - // imm32 = ZeroExtend(imm8:Õ00Õ, 32); regs = UInt(imm8); + // imm32 = ZeroExtend(imm8:'00', 32); regs = UInt(imm8); imm32 = Bits32 (opcode, 7, 0) << 2; regs = Bits32 (opcode, 7, 0); @@ -11193,7 +11196,7 @@ EmulateInstructionARM::EmulateVLDR (const uint32_t opcode, ARMEncoding encoding) { case eEncodingT1: case eEncodingA1: - // single_reg = FALSE; add = (U == Ô1Õ); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // single_reg = FALSE; add = (U == '1'); imm32 = ZeroExtend(imm8:'00', 32); single_reg = false; add = BitIsSet (opcode, 23); imm32 = Bits32 (opcode, 7, 0) << 2; @@ -11206,7 +11209,7 @@ EmulateInstructionARM::EmulateVLDR (const uint32_t opcode, ARMEncoding encoding) case eEncodingT2: case eEncodingA2: - // single_reg = TRUE; add = (U == Ô1Õ); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // single_reg = TRUE; add = (U == '1'); imm32 = ZeroExtend(imm8:'00', 32); single_reg = true; add = BitIsSet (opcode, 23); imm32 = Bits32 (opcode, 7, 0) << 2; @@ -11322,7 +11325,7 @@ EmulateInstructionARM::EmulateVSTR (const uint32_t opcode, ARMEncoding encoding) { case eEncodingT1: case eEncodingA1: - // single_reg = FALSE; add = (U == Ô1Õ); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // single_reg = FALSE; add = (U == '1'); imm32 = ZeroExtend(imm8:'00', 32); single_reg = false; add = BitIsSet (opcode, 23); imm32 = Bits32 (opcode, 7, 0) << 2; @@ -11339,7 +11342,7 @@ EmulateInstructionARM::EmulateVSTR (const uint32_t opcode, ARMEncoding encoding) case eEncodingT2: case eEncodingA2: - // single_reg = TRUE; add = (U == Ô1Õ); imm32 = ZeroExtend(imm8:Õ00Õ, 32); + // single_reg = TRUE; add = (U == '1'); imm32 = ZeroExtend(imm8:'00', 32); single_reg = true; add = BitIsSet (opcode, 23); imm32 = Bits32 (opcode, 7, 0) << 2; @@ -11461,16 +11464,16 @@ EmulateInstructionARM::EmulateVLD1Multiple (const uint32_t opcode, ARMEncoding e case eEncodingA1: { // case type of - // when Ô0111Õ - // regs = 1; if align<1> == Ô1Õ then UNDEFINED; - // when Ô1010Õ - // regs = 2; if align == Ô11Õ then UNDEFINED; - // when Ô0110Õ - // regs = 3; if align<1> == Ô1Õ then UNDEFINED; - // when Ô0010Õ + // when '0111' + // regs = 1; if align<1> == '1' then UNDEFINED; + // when '1010' + // regs = 2; if align == '11' then UNDEFINED; + // when '0110' + // regs = 3; if align<1> == '1' then UNDEFINED; + // when '0010' // regs = 4; // otherwise - // SEE ÒRelated encodingsÓ; + // SEE 'Related encodings'; uint32_t type = Bits32 (opcode, 11, 8); uint32_t align = Bits32 (opcode, 5, 4); if (type == 7) // '0111' @@ -11499,7 +11502,7 @@ EmulateInstructionARM::EmulateVLD1Multiple (const uint32_t opcode, ARMEncoding e else return false; - // alignment = if align == Ô00Õ then 1 else 4 << UInt(align); + // alignment = if align == '00' then 1 else 4 << UInt(align); if (align == 0) alignment = 1; else @@ -11624,13 +11627,13 @@ EmulateInstructionARM::EmulateVLD1Single (const uint32_t opcode, const ARMEncodi { uint32_t size = Bits32 (opcode, 11, 10); uint32_t index_align = Bits32 (opcode, 7, 4); - // if size == Ô11Õ then SEE VLD1 (single element to all lanes); + // if size == '11' then SEE VLD1 (single element to all lanes); if (size == 3) return EmulateVLD1SingleAll (opcode, encoding); // case size of if (size == 0) // when '00' { - // if index_align<0> != Ô0Õ then UNDEFINED; + // if index_align<0> != '0' then UNDEFINED; if (BitIsClear (index_align, 0)) return false; @@ -11640,9 +11643,9 @@ EmulateInstructionARM::EmulateVLD1Single (const uint32_t opcode, const ARMEncodi index = Bits32 (index_align, 3, 1); alignment = 1; } - else if (size == 1) // when Ô01Õ + else if (size == 1) // when '01' { - // if index_align<1> != Ô0Õ then UNDEFINED; + // if index_align<1> != '0' then UNDEFINED; if (BitIsClear (index_align, 1)) return false; @@ -11651,19 +11654,19 @@ EmulateInstructionARM::EmulateVLD1Single (const uint32_t opcode, const ARMEncodi esize = 16; index = Bits32 (index_align, 3, 2); - // alignment = if index_align<0> == Ô0Õ then 1 else 2; + // alignment = if index_align<0> == '0' then 1 else 2; if (BitIsClear (index_align, 0)) alignment = 1; else alignment = 2; } - else if (size == 2) // when Ô10Õ + else if (size == 2) // when '10' { - // if index_align<2> != Ô0Õ then UNDEFINED; + // if index_align<2> != '0' then UNDEFINED; if (BitIsClear (index_align, 2)) return false; - // if index_align<1:0> != Ô00Õ && index_align<1:0> != Ô11Õ then UNDEFINED; + // if index_align<1:0> != '00' && index_align<1:0> != '11' then UNDEFINED; if ((Bits32 (index_align, 1, 0) != 0) && (Bits32 (index_align, 1, 0) != 3)) return false; @@ -11672,7 +11675,7 @@ EmulateInstructionARM::EmulateVLD1Single (const uint32_t opcode, const ARMEncodi esize = 32; index = Bit32 (index_align, 3); - // alignment = if index_align<1:0> == Ô00Õ then 1 else 4; + // alignment = if index_align<1:0> == '00' then 1 else 4; if (Bits32 (index_align, 1, 0) == 0) alignment = 1; else @@ -11806,35 +11809,35 @@ EmulateInstructionARM::EmulateVST1Multiple (const uint32_t opcode, ARMEncoding e uint32_t align = Bits32 (opcode, 5, 4); // case type of - if (type == 7) // when Ô0111Õ + if (type == 7) // when '0111' { - // regs = 1; if align<1> == Ô1Õ then UNDEFINED; + // regs = 1; if align<1> == '1' then UNDEFINED; regs = 1; if (BitIsSet (align, 1)) return false; } - else if (type == 10) // when Ô1010Õ + else if (type == 10) // when '1010' { - // regs = 2; if align == Ô11Õ then UNDEFINED; + // regs = 2; if align == '11' then UNDEFINED; regs = 2; if (align == 3) return false; } - else if (type == 6) // when Ô0110Õ + else if (type == 6) // when '0110' { - // regs = 3; if align<1> == Ô1Õ then UNDEFINED; + // regs = 3; if align<1> == '1' then UNDEFINED; regs = 3; if (BitIsSet (align, 1)) return false; } - else if (type == 2) // when Ô0010Õ + else if (type == 2) // when '0010' // regs = 4; regs = 4; else // otherwise - // SEE ÒRelated encodingsÓ; + // SEE 'Related encodings'; return false; - // alignment = if align == Ô00Õ then 1 else 4 << UInt(align); + // alignment = if align == '00' then 1 else 4 << UInt(align); if (align == 0) alignment = 1; else @@ -11964,14 +11967,14 @@ EmulateInstructionARM::EmulateVST1Single (const uint32_t opcode, ARMEncoding enc uint32_t size = Bits32 (opcode, 11, 10); uint32_t index_align = Bits32 (opcode, 7, 4); - // if size == Ô11Õ then UNDEFINED; + // if size == '11' then UNDEFINED; if (size == 3) return false; // case size of - if (size == 0) // when Ô00Õ + if (size == 0) // when '00' { - // if index_align<0> != Ô0Õ then UNDEFINED; + // if index_align<0> != '0' then UNDEFINED; if (BitIsClear (index_align, 0)) return false; // ebytes = 1; esize = 8; index = UInt(index_align<3:1>); alignment = 1; @@ -11980,9 +11983,9 @@ EmulateInstructionARM::EmulateVST1Single (const uint32_t opcode, ARMEncoding enc index = Bits32 (index_align, 3, 1); alignment = 1; } - else if (size == 1) // when Ô01Õ + else if (size == 1) // when '01' { - // if index_align<1> != Ô0Õ then UNDEFINED; + // if index_align<1> != '0' then UNDEFINED; if (BitIsClear (index_align, 1)) return false; @@ -11991,19 +11994,19 @@ EmulateInstructionARM::EmulateVST1Single (const uint32_t opcode, ARMEncoding enc esize = 16; index = Bits32 (index_align, 3, 2); - // alignment = if index_align<0> == Ô0Õ then 1 else 2; + // alignment = if index_align<0> == '0' then 1 else 2; if (BitIsClear (index_align, 0)) alignment = 1; else alignment = 2; } - else if (size == 2) // when Ô10Õ + else if (size == 2) // when '10' { - // if index_align<2> != Ô0Õ then UNDEFINED; + // if index_align<2> != '0' then UNDEFINED; if (BitIsClear (index_align, 2)) return false; - // if index_align<1:0> != Ô00Õ && index_align<1:0> != Ô11Õ then UNDEFINED; + // if index_align<1:0> != '00' && index_align<1:0> != '11' then UNDEFINED; if ((Bits32 (index_align, 1, 0) != 0) && (Bits32 (index_align, 1, 0) != 3)) return false; @@ -12012,7 +12015,7 @@ EmulateInstructionARM::EmulateVST1Single (const uint32_t opcode, ARMEncoding enc esize = 32; index = Bit32 (index_align, 3); - // alignment = if index_align<1:0> == Ô00Õ then 1 else 4; + // alignment = if index_align<1:0> == '00' then 1 else 4; if (Bits32 (index_align, 1, 0) == 0) alignment = 1; else @@ -12125,12 +12128,12 @@ EmulateInstructionARM::EmulateVLD1SingleAll (const uint32_t opcode, const ARMEnc case eEncodingT1: case eEncodingA1: { - //if size == Ô11Õ || (size == Ô00Õ && a == Ô1Õ) then UNDEFINED; + //if size == '11' || (size == '00' && a == '1') then UNDEFINED; uint32_t size = Bits32 (opcode, 7, 6); if ((size == 3) || ((size == 0) && BitIsSet (opcode, 4))) return false; - //ebytes = 1 << UInt(size); elements = 8 DIV ebytes; regs = if T == Ô0Õ then 1 else 2; + //ebytes = 1 << UInt(size); elements = 8 DIV ebytes; regs = if T == '0' then 1 else 2; ebytes = 1 << size; elements = 8 / ebytes; if (BitIsClear (opcode, 5)) @@ -12138,7 +12141,7 @@ EmulateInstructionARM::EmulateVLD1SingleAll (const uint32_t opcode, const ARMEnc else regs = 2; - //alignment = if a == Ô0Õ then 1 else ebytes; + //alignment = if a == '0' then 1 else ebytes; if (BitIsClear (opcode, 4)) alignment = 1; else @@ -12235,19 +12238,19 @@ EmulateInstructionARM::EmulateSUBSPcLrEtc (const uint32_t opcode, const ARMEncod UNPREDICTABLE; operand2 = if register_form then Shift(R[m], shift_t, shift_n, APSR.C) else imm32; case opcode of - when Ô0000Õ result = R[n] AND operand2; // AND - when Ô0001Õ result = R[n] EOR operand2; // EOR - when Ô0010Õ (result, -, -) = AddWithCarry(R[n], NOT(operand2), Ô1Õ); // SUB - when Ô0011Õ (result, -, -) = AddWithCarry(NOT(R[n]), operand2, Ô1Õ); // RSB - when Ô0100Õ (result, -, -) = AddWithCarry(R[n], operand2, Ô0Õ); // ADD - when Ô0101Õ (result, -, -) = AddWithCarry(R[n], operand2, APSR.c); // ADC - when Ô0110Õ (result, -, -) = AddWithCarry(R[n], NOT(operand2), APSR.C); // SBC - when Ô0111Õ (result, -, -) = AddWithCarry(NOT(R[n]), operand2, APSR.C); // RSC - when Ô1100Õ result = R[n] OR operand2; // ORR - when Ô1101Õ result = operand2; // MOV - when Ô1110Õ result = R[n] AND NOT(operand2); // BIC - when Ô1111Õ result = NOT(operand2); // MVN - CPSRWriteByInstr(SPSR[], Ô1111Õ, TRUE); + when '0000' result = R[n] AND operand2; // AND + when '0001' result = R[n] EOR operand2; // EOR + when '0010' (result, -, -) = AddWithCarry(R[n], NOT(operand2), '1'); // SUB + when '0011' (result, -, -) = AddWithCarry(NOT(R[n]), operand2, '1'); // RSB + when '0100' (result, -, -) = AddWithCarry(R[n], operand2, '0'); // ADD + when '0101' (result, -, -) = AddWithCarry(R[n], operand2, APSR.c); // ADC + when '0110' (result, -, -) = AddWithCarry(R[n], NOT(operand2), APSR.C); // SBC + when '0111' (result, -, -) = AddWithCarry(NOT(R[n]), operand2, APSR.C); // RSC + when '1100' result = R[n] OR operand2; // ORR + when '1101' result = operand2; // MOV + when '1110' result = R[n] AND NOT(operand2); // BIC + when '1111' result = NOT(operand2); // MVN + CPSRWriteByInstr(SPSR[], '1111', TRUE); BranchWritePC(result); #endif @@ -12267,7 +12270,7 @@ EmulateInstructionARM::EmulateSUBSPcLrEtc (const uint32_t opcode, const ARMEncod { case eEncodingT1: // if CurrentInstrSet() == InstrSet_ThumbEE then UNPREDICTABLE - // n = 14; imm32 = ZeroExtend(imm8, 32); register_form = FALSE; opcode = Ô0010Õ; // = SUB + // n = 14; imm32 = ZeroExtend(imm8, 32); register_form = FALSE; opcode = '0010'; // = SUB n = 14; imm32 = Bits32 (opcode, 7, 0); register_form = false; @@ -12329,62 +12332,62 @@ EmulateInstructionARM::EmulateSUBSPcLrEtc (const uint32_t opcode, const ARMEncod // case opcode of switch (code) { - case 0: // when Ô0000Õ + case 0: // when '0000' // result = R[n] AND operand2; // AND result.result = Rn & operand2; break; - case 1: // when Ô0001Õ + case 1: // when '0001' // result = R[n] EOR operand2; // EOR result.result = Rn ^ operand2; break; - case 2: // when Ô0010Õ - // (result, -, -) = AddWithCarry(R[n], NOT(operand2), Ô1Õ); // SUB + case 2: // when '0010' + // (result, -, -) = AddWithCarry(R[n], NOT(operand2), '1'); // SUB result = AddWithCarry (Rn, ~(operand2), 1); break; - case 3: // when Ô0011Õ - // (result, -, -) = AddWithCarry(NOT(R[n]), operand2, Ô1Õ); // RSB + case 3: // when '0011' + // (result, -, -) = AddWithCarry(NOT(R[n]), operand2, '1'); // RSB result = AddWithCarry (~(Rn), operand2, 1); break; - case 4: // when Ô0100Õ - // (result, -, -) = AddWithCarry(R[n], operand2, Ô0Õ); // ADD + case 4: // when '0100' + // (result, -, -) = AddWithCarry(R[n], operand2, '0'); // ADD result = AddWithCarry (Rn, operand2, 0); break; - case 5: // when Ô0101Õ + case 5: // when '0101' // (result, -, -) = AddWithCarry(R[n], operand2, APSR.c); // ADC result = AddWithCarry (Rn, operand2, APSR_C); break; - case 6: // when Ô0110Õ + case 6: // when '0110' // (result, -, -) = AddWithCarry(R[n], NOT(operand2), APSR.C); // SBC result = AddWithCarry (Rn, ~(operand2), APSR_C); break; - case 7: // when Ô0111Õ + case 7: // when '0111' // (result, -, -) = AddWithCarry(NOT(R[n]), operand2, APSR.C); // RSC result = AddWithCarry (~(Rn), operand2, APSR_C); break; - case 10: // when Ô1100Õ + case 10: // when '1100' // result = R[n] OR operand2; // ORR result.result = Rn | operand2; break; - case 11: // when Ô1101Õ + case 11: // when '1101' // result = operand2; // MOV result.result = operand2; break; - case 12: // when Ô1110Õ + case 12: // when '1110' // result = R[n] AND NOT(operand2); // BIC result.result = Rn & ~(operand2); break; - case 15: // when Ô1111Õ + case 15: // when '1111' // result = NOT(operand2); // MVN result.result = ~(operand2); break; @@ -12392,7 +12395,7 @@ EmulateInstructionARM::EmulateSUBSPcLrEtc (const uint32_t opcode, const ARMEncod default: return false; } - // CPSRWriteByInstr(SPSR[], Ô1111Õ, TRUE); + // CPSRWriteByInstr(SPSR[], '1111', TRUE); // For now, in emulation mode, we don't have access to the SPSR, so we will use the CPSR instead, and hope for // the best. @@ -13076,7 +13079,7 @@ EmulateInstructionARM::ArchVersion () } bool -EmulateInstructionARM::ConditionPassed (const uint32_t opcode, bool *is_conditional) +EmulateInstructionARM::ConditionPassed (const uint32_t opcode) { // If we are ignoring conditions, then always return true. // this allows us to iterate over disassembly code and still @@ -13084,12 +13087,8 @@ EmulateInstructionARM::ConditionPassed (const uint32_t opcode, bool *is_conditio // bits set in the CPSR register... if (m_ignore_conditions) return true; - - if (is_conditional) - *is_conditional = true; const uint32_t cond = CurrentCond (opcode); - if (cond == UINT32_MAX) return false; @@ -13149,8 +13148,6 @@ EmulateInstructionARM::ConditionPassed (const uint32_t opcode, bool *is_conditio case 7: // Always execute (cond == 0b1110, or the special 0b1111 which gives // opcodes different meanings, but always means execution happens. - if (is_conditional) - *is_conditional = false; return true; } @@ -13643,6 +13640,13 @@ EmulateInstructionARM::EvaluateInstruction (uint32_t evaluate_options) } bool +EmulateInstructionARM::IsInstructionConditional() +{ + const uint32_t cond = CurrentCond (m_opcode.GetOpcode32()); + return cond != 0xe && cond != 0xf && cond != UINT32_MAX; +} + +bool EmulateInstructionARM::TestEmulation (Stream *out_stream, ArchSpec &arch, OptionValueDictionary *test_data) { if (!test_data) |