about summary refs log tree commit diff stats
path: root/miasm2/analysis/disasm_cb.py
diff options
context:
space:
mode:
Diffstat (limited to 'miasm2/analysis/disasm_cb.py')
-rw-r--r--miasm2/analysis/disasm_cb.py137
1 files changed, 137 insertions, 0 deletions
diff --git a/miasm2/analysis/disasm_cb.py b/miasm2/analysis/disasm_cb.py
new file mode 100644
index 00000000..4b4832f8
--- /dev/null
+++ b/miasm2/analysis/disasm_cb.py
@@ -0,0 +1,137 @@
+#!/usr/bin/env python
+#-*- coding:utf-8 -*-
+
+from miasm2.expression.expression import *
+from miasm2.expression.simplifications import expr_simp
+from miasm2.core.asmbloc import *
+from miasm2.core.utils import *
+# from miasm2.core.graph import DiGraph
+
+
+def get_ira(mnemo, attrib):
+    arch = mnemo.name, attrib
+    if arch == ("arm", "arm"):
+        from miasm2.arch.arm.ira import ir_a_arm_base as ira
+    elif arch == ("x86", 32):
+        from miasm2.arch.x86.ira import ir_a_x86_32 as ira
+    elif arch == ("x86", 64):
+        from miasm2.arch.x86.ira import ir_a_x86_64 as ira
+    else:
+        raise ValueError('unknown architecture: %s' % mnemo.name)
+    return ira
+
+
+def arm_guess_subcall(
+    mnemo, attrib, pool_bin, cur_bloc, offsets_to_dis, symbol_pool):
+    ira = get_ira(mnemo, attrib)
+
+    sp = asm_symbol_pool()
+    my_ir = ira(sp)
+    print '###'
+    print cur_bloc
+    my_ir.add_bloc(cur_bloc)
+
+    ir_blocs = my_ir.blocs.values()
+    # flow_graph = DiGraph()
+    to_add = set()
+    for irb in ir_blocs:
+        # print 'X'*40
+        # print irb
+        pc_val = None
+        lr_val = None
+        for exprs in irb.irs:
+            for e in exprs:
+                if e.dst == my_ir.pc:
+                    pc_val = e.src
+                if e.dst == mnemo.regs.LR:
+                    lr_val = e.src
+        if pc_val is None or lr_val is None:
+            continue
+        if not isinstance(lr_val, ExprInt):
+            continue
+
+        l = cur_bloc.lines[-1]
+        if lr_val.arg != l.offset + l.l:
+            continue
+        # print 'IS CALL!'
+        l = symbol_pool.getby_offset_create(int(lr_val.arg))
+        c = asm_constraint_next(l)
+
+        to_add.add(c)
+        offsets_to_dis.add(int(lr_val.arg))
+
+    # if to_add:
+    #    print 'R'*70
+    for c in to_add:
+        # print c
+        cur_bloc.addto(c)
+
+
+def arm_guess_jump_table(
+    mnemo, attrib, pool_bin, cur_bloc, offsets_to_dis, symbol_pool):
+    ira = get_ira(mnemo, attrib)
+
+    jra = ExprId('jra')
+    jrb = ExprId('jrb')
+
+    sp = asm_symbol_pool()
+    my_ir = ira(sp)
+    my_ir.add_bloc(cur_bloc)
+
+    ir_blocs = my_ir.blocs.values()
+    for irb in ir_blocs:
+        # print 'X'*40
+        # print irb
+        pc_val = None
+        # lr_val = None
+        for exprs in irb.irs:
+            for e in exprs:
+                if e.dst == my_ir.pc:
+                    pc_val = e.src
+                # if e.dst == mnemo.regs.LR:
+                #    lr_val = e.src
+        if pc_val is None:
+            continue
+        if not isinstance(pc_val, ExprMem):
+            continue
+        assert(pc_val.size == 32)
+        print pc_val
+        ad = pc_val.arg
+        ad = expr_simp(ad)
+        print ad
+        res = MatchExpr(ad, jra + jrb, set([jra, jrb]))
+        if res is False:
+            raise NotImplementedError('not fully functional')
+        print res
+        if not isinstance(res[jrb], ExprInt):
+            raise NotImplementedError('not fully functional')
+        base_ad = int(res[jrb].arg)
+        print base_ad
+        addrs = set()
+        i = -1
+        max_table_entry = 10000
+        max_diff_addr = 0x100000  # heuristic
+        while i < max_table_entry:
+            i += 1
+            try:
+                ad = upck32(pool_bin.getbytes(base_ad + 4 * i, 4))
+            except:
+                break
+            if abs(ad - base_ad) > max_diff_addr:
+                break
+            addrs.add(ad)
+        print [hex(x) for x in addrs]
+
+        for ad in addrs:
+            offsets_to_dis.add(ad)
+            l = symbol_pool.getby_offset_create(ad)
+            c = asm_constraint_to(l)
+            cur_bloc.addto(c)
+
+guess_funcs = []
+
+
+def guess_multi_cb(
+    mnemo, attrib, pool_bin, cur_bloc, offsets_to_dis, symbol_pool):
+    for f in guess_funcs:
+        f(mnemo, attrib, pool_bin, cur_bloc, offsets_to_dis, symbol_pool)