Exemple #1
0
def _translate_lsl(self, tb, instruction):
    # LSL (register)
    if len(instruction.operands) == 3 and isinstance(instruction.operands[1], ArmRegisterOperand):
        sh_op = ArmShiftedRegisterOperand(instruction.operands[1], "lsl", instruction.operands[2],
                                          instruction.operands[1].size)
        disp = tb._compute_shifted_register(sh_op)
        tb.write(instruction.operands[0], disp)
        return

    if len(instruction.operands) == 2 and isinstance(instruction.operands[1], ArmShiftedRegisterOperand):
        # Capstone is incorrectly packing <Rm>, #<imm5> into a shifted register, unpack it
        instruction.operands.append(instruction.operands[1]._shift_amount)
        instruction.operands[1] = instruction.operands[1]._base_reg

    oprnd1 = tb.read(instruction.operands[1])
    oprnd2 = tb.read(instruction.operands[2])
    result = tb.temporal(oprnd1.size)

    tb.add(self._builder.gen_bsh(oprnd1, oprnd2, result))
    tb.write(instruction.operands[0], result)

    if instruction.update_flags:
        self._update_zf(tb, oprnd1, oprnd2, result)
        self._update_nf(tb, oprnd1, oprnd2, result)
        # TODO: Encapsulate this new kind of flag update (different from the data proc instructions like add, and, orr)
        if oprnd2.immediate == 0:
            return
        else:
            # carry_out = Rm[32 - shift_imm]
            shift_carry_out = tb._extract_bit(oprnd1, 32 - oprnd2.immediate)
            tb.add(self._builder.gen_str(shift_carry_out, self._flags["cf"]))
Exemple #2
0
def process_shifted_register(tokens):

    base = process_register(tokens["base"])
    sh_type = tokens["type"]
    amount = tokens.get("amount", None)

    if amount:
        if "imm" in amount:
            amount = ArmImmediateOperand("".join(amount["imm"]), arch_info.operand_size)
        elif "reg" in amount:
            amount = process_register(amount["reg"])
        else:
            raise Exception("Unknown amount type.")

    return ArmShiftedRegisterOperand(base, sh_type, amount, base.size)
    def __cs_shift_to_arm_op(self, cs_op, cs_insn, arm_base):
        if cs_op.shift.type == 0:
            raise Exception("Invalid shift type.")

        cs_shift_mapper = {
            ARM_SFT_ASR: "asr",
            ARM_SFT_LSL: "lsl",
            ARM_SFT_LSR: "lsr",
            ARM_SFT_ROR: "ror",
            ARM_SFT_RRX: "rrx",
            ARM_SFT_ASR_REG: "asr",
            ARM_SFT_LSL_REG: "lsl",
            ARM_SFT_LSR_REG: "lsr",
            ARM_SFT_ROR_REG: "ror",
            ARM_SFT_RRX_REG: "rrx",
        }

        # The base register (arm_base) is not included in the shift
        # struct in Capstone, so it's provided separately.
        sh_type = cs_shift_mapper[cs_op.shift.type]

        if cs_op.shift.type <= ARM_SFT_RRX:
            amount = ArmImmediateOperand(cs_op.shift.value,
                                         self._arch_info.operand_size)

            # TODO: check if this is a valid case.
            if cs_op.shift.value == 0:
                raise Exception("Shift value is zero.")
        elif cs_op.shift.type <= ARM_SFT_RRX_REG:
            amount = self.__cs_reg_idx_to_arm_op_reg(cs_op.shift.value,
                                                     cs_insn)
        else:
            raise Exception("Unknown shift type.")

        return ArmShiftedRegisterOperand(arm_base, sh_type, amount,
                                         arm_base.size)