Example #1
0
    def __extract_rename_info(cfunc, ctree_item):
        # type: (idaapi.cfunc_t, idaapi.ctree_item_t) -> (idaapi.lvar_t, str)

        if ctree_item.citype != idaapi.VDI_EXPR:
            return

        expression = ctree_item.it.to_specific_type
        if expression.op != idaapi.cot_var:
            return

        parent = cfunc.body.find_parent_of(expression).to_specific_type
        if parent.op != idaapi.cot_call or parent.x.obj_ea == idaapi.BADADDR:
            return

        lvar = ctree_item.get_lvar()
        arg_index, _ = helper.get_func_argument_info(parent, expression)
        func_tinfo = parent.x.type.get_pointed_object()
        arg_name = helper.get_func_arg_name(func_tinfo, arg_index)
        if arg_name and _should_be_renamed(lvar.name, arg_name):
            return lvar, arg_name.lstrip("_")
Example #2
0
    def activate(self, ctx):
        hx_view = idaapi.get_widget_vdui(ctx.widget)
        if not self.__can_be_part_of_assert(hx_view.cfunc, hx_view.item):
            return

        # So we clicked on function an func argument that is a string. Now we extract
        # argument index and address of assert function
        expr_arg = hx_view.item.it.to_specific_type
        expr_call = hx_view.cfunc.body.find_parent_of(
            expr_arg).to_specific_type
        arg_idx, _ = helper.get_func_argument_info(expr_call, expr_arg)
        assert_func_ea = expr_call.x.obj_ea

        # Iterate through all places where assert function and rename using helper class
        all_callers = helper.get_funcs_calling_address(assert_func_ea)
        for caller_ea in all_callers:
            cfunc = helper.decompile_function(caller_ea)
            if cfunc:
                _RenameUsingAssertVisitor(cfunc, assert_func_ea,
                                          arg_idx).process()

        hx_view.refresh_view(True)
Example #3
0
    def extract_recast_info(self, cfunc, ctree_item):
        # type: (idaapi.cfunc_t, idaapi.ctree_item_t) -> namedtuple
        # Returns one of the Recast... namedtuple or None if nothing was found

        if ctree_item.citype != idaapi.VDI_EXPR:
            return

        expression = ctree_item.it.to_specific_type
        child = None

        # Look through parents until we found Return, Assignment or Call
        while expression and expression.op not in (idaapi.cot_asg,
                                                   idaapi.cit_return,
                                                   idaapi.cot_call):
            child = expression.to_specific_type
            expression = cfunc.body.find_parent_of(expression)
        if not expression:
            return

        expression = expression.to_specific_type
        if expression.op == idaapi.cot_asg:

            if expression.x.opname not in ('var', 'obj', 'memptr', 'memref'):
                return

            right_expr = expression.y
            right_tinfo = right_expr.x.type if right_expr.op == idaapi.cot_cast else right_expr.type

            # Check if both left and right parts of expression are of the same types.
            # If not then we can recast then.
            if right_tinfo.dstr() == expression.x.type.dstr():
                return

            if expression.x.op == idaapi.cot_var:
                # var = (TYPE ) ...;
                variable = cfunc.get_lvars()[expression.x.v.idx]
                return RecastLocalVariable(right_tinfo, variable)

            elif expression.x.op == idaapi.cot_obj:
                # g_var = (TYPE ) ...;
                return RecastGlobalVariable(right_tinfo, expression.x.obj_ea)

            elif expression.x.op == idaapi.cot_memptr:
                # struct->member = (TYPE ) ...;
                struct_name = expression.x.x.type.get_pointed_object().dstr()
                struct_offset = expression.x.m
                return RecastStructure(right_tinfo, struct_name, struct_offset)

            elif expression.x.op == idaapi.cot_memref:
                # struct.member = (TYPE ) ...;
                struct_name = expression.x.x.type.dstr()
                struct_offset = expression.x.m
                return RecastStructure(right_tinfo, struct_name, struct_offset)

        elif expression.op == idaapi.cit_return:
            child = child or expression.creturn.expr
            if child.op == idaapi.cot_cast:
                # return (TYPE) ...;
                return RecastReturn(child.x.type, cfunc.entry_ea)

            func_tinfo = idaapi.tinfo_t()
            cfunc.get_func_type(func_tinfo)
            rettype = func_tinfo.get_rettype()
            if rettype.dstr() != child.type.dstr():
                # return ...;
                # This's possible when returned type and value are both pointers to different types
                return RecastReturn(child.type, cfunc.entry_ea)

        elif expression.op == idaapi.cot_call:
            if expression.x == child:
                return
            func_ea = expression.x.obj_ea
            arg_index, param_tinfo = helper.get_func_argument_info(
                expression, child)
            if expression.x.op == idaapi.cot_memptr:
                if child.op == idaapi.cot_cast:
                    # struct_ptr->func(..., (TYPE) var, ...);
                    arg_tinfo = child.x.type
                else:
                    # struct_ptr->func(..., var, ...); When `var` and `arg` are different pointers
                    if param_tinfo.equals_to(child.type):
                        return
                    arg_tinfo = child.type

                struct_tinfo = expression.x.x.type.get_pointed_object()
                funcptr_tinfo = expression.x.type
                helper.set_funcptr_argument(funcptr_tinfo, arg_index,
                                            arg_tinfo)
                return RecastStructure(funcptr_tinfo, struct_tinfo.dstr(),
                                       expression.x.m)

            if child.op == idaapi.cot_ref:
                if child.x.op == idaapi.cot_memref and child.x.m == 0:
                    # func(..., &struct.field_0, ...)
                    arg_tinfo = idaapi.tinfo_t()
                    arg_tinfo.create_ptr(child.x.x.type)
                elif child.x.op == idaapi.cot_memptr and child.x.m == 0:
                    # func(..., &struct->field_0, ...)
                    arg_tinfo = child.x.x.type
                else:
                    # func(..., &var, ...)
                    arg_tinfo = child.type
            elif child.op == idaapi.cot_cast:
                arg_tinfo = child.x.type
            else:
                arg_tinfo = child.type

            func_tinfo = expression.x.type.get_pointed_object()
            return RecastArgument(arg_tinfo, arg_index, func_ea, func_tinfo)