diff options
| author | serpilliere <devnull@localhost> | 2014-06-17 13:09:31 +0200 |
|---|---|---|
| committer | serpilliere <devnull@localhost> | 2014-06-17 13:09:31 +0200 |
| commit | 180b3907cdfcda2e8f3bd719b1d3531ba2e32a5f (patch) | |
| tree | c91a5e6564ac6579f0a97d9a913540708464f8c3 | |
| parent | 1a1f8fb1bf35def45e651452eb5db27d36486dda (diff) | |
| parent | b4672a0881de3a62d6ea711603870db9a28f6cce (diff) | |
| download | miasm-180b3907cdfcda2e8f3bd719b1d3531ba2e32a5f.tar.gz miasm-180b3907cdfcda2e8f3bd719b1d3531ba2e32a5f.zip | |
merge
| -rw-r--r-- | miasm2/arch/arm/regs.py | 2 | ||||
| -rw-r--r-- | miasm2/arch/msp430/regs.py | 2 | ||||
| -rw-r--r-- | miasm2/arch/sh4/regs.py | 2 | ||||
| -rw-r--r-- | miasm2/arch/x86/regs.py | 19 | ||||
| -rw-r--r-- | miasm2/jitter/jitcore_python.py | 89 | ||||
| -rw-r--r-- | miasm2/jitter/vm_mngr_py.c | 19 | ||||
| -rw-r--r-- | test/test_all.py | 48 |
7 files changed, 122 insertions, 59 deletions
diff --git a/miasm2/arch/arm/regs.py b/miasm2/arch/arm/regs.py index 6ddac2ef..2787605a 100644 --- a/miasm2/arch/arm/regs.py +++ b/miasm2/arch/arm/regs.py @@ -66,6 +66,8 @@ all_regs_ids = [ zf, nf, of, cf ] +all_regs_ids_no_alias = all_regs_ids + all_regs_ids_byname = dict([(x.name, x) for x in all_regs_ids]) all_regs_ids_init = [R0_init, R1_init, R2_init, R3_init, diff --git a/miasm2/arch/msp430/regs.py b/miasm2/arch/msp430/regs.py index 7a389ae1..ea86e1fc 100644 --- a/miasm2/arch/msp430/regs.py +++ b/miasm2/arch/msp430/regs.py @@ -89,6 +89,8 @@ all_regs_ids = [ cpuoff, gie, osc, scg0, scg1, res, ] +all_regs_ids_no_alias = all_regs_ids + all_regs_ids_byname = dict([(x.name, x) for x in all_regs_ids]) all_regs_ids_init = [PC_init, SP_init, SR_init, R3_init, diff --git a/miasm2/arch/sh4/regs.py b/miasm2/arch/sh4/regs.py index bfc61b04..6ffe9691 100644 --- a/miasm2/arch/sh4/regs.py +++ b/miasm2/arch/sh4/regs.py @@ -70,6 +70,8 @@ all_regs_ids = [ PC, PR, R0, GBR, SR, VBR, SSR, SPC, SGR, DBR, MACH, MACL, FPUL, FR0] +all_regs_ids_no_alias = all_regs_ids + all_regs_ids_byname = dict([(x.name, x) for x in all_regs_ids]) all_regs_ids_init = [ExprId("%s_init" % x.name, x.size) for x in all_regs_ids] diff --git a/miasm2/arch/x86/regs.py b/miasm2/arch/x86/regs.py index 532b4f0c..293f81e7 100644 --- a/miasm2/arch/x86/regs.py +++ b/miasm2/arch/x86/regs.py @@ -384,6 +384,25 @@ all_regs_ids = [ exception_flags, ] + fltregs32_expr +all_regs_ids_no_alias = [ + RAX, RBX, RCX, RDX, RSP, RBP, RIP, RSI, RDI, + R8, R9, R10, R11, R12, R13, R14, R15, R15, + zf, nf, pf, of, cf, af, df, + tf, i_f, iopl, nt, rf, vm, ac, vif, vip, i_d, + float_control, float_eip, float_cs, float_address, float_ds, + tsc1, tsc2, + ES, CS, SS, DS, FS, GS, + float_st0, float_st1, float_st2, float_st3, + float_st4, float_st5, float_st6, float_st7, + float_c0, float_c1, float_c2, float_c3, + cr0, cr3, + dr0, dr1, dr2, dr3, dr4, dr5, dr6, dr7, + float_stack_ptr, + mm0, mm1, mm2, mm3, mm4, mm5, mm6, mm7, + + exception_flags, +] + fltregs32_expr + all_regs_ids_byname = dict([(x.name, x) for x in all_regs_ids]) all_regs_ids_init = [ExprId("%s_init" % x.name, x.size) for x in all_regs_ids] diff --git a/miasm2/jitter/jitcore_python.py b/miasm2/jitter/jitcore_python.py index e054efa5..90c8bace 100644 --- a/miasm2/jitter/jitcore_python.py +++ b/miasm2/jitter/jitcore_python.py @@ -1,9 +1,51 @@ import miasm2.jitter.jitcore as jitcore import miasm2.expression.expression as m2_expr +import miasm2.jitter.csts as csts from miasm2.expression.simplifications import expr_simp from miasm2.ir.symbexec import symbexec +################################################################################ +# Util methods for Python jitter # +################################################################################ + +def update_cpu_from_engine(cpu, exec_engine): + """Updates @cpu instance according to new CPU values + @cpu: JitCpu instance + @exec_engine: symbexec instance""" + + for symbol in exec_engine.symbols: + if isinstance(symbol, m2_expr.ExprId): + if hasattr(cpu, symbol.name): + value = exec_engine.symbols.symbols_id[symbol] + if not isinstance(value, m2_expr.ExprInt): + raise ValueError("A simplification is missing: %s" % value) + + setattr(cpu, symbol.name, value.arg.arg) + else: + raise NotImplementedError("Type not handled: %s" % symbol) + + +def update_engine_from_cpu(cpu, exec_engine): + """Updates CPU values according to @cpu instance + @cpu: JitCpu instance + @exec_engine: symbexec instance""" + + for symbol in exec_engine.symbols: + if isinstance(symbol, m2_expr.ExprId): + if hasattr(cpu, symbol.name): + value = m2_expr.ExprInt_fromsize(symbol.size, + getattr(cpu, symbol.name)) + exec_engine.symbols.symbols_id[symbol] = value + else: + raise NotImplementedError("Type not handled: %s" % symbol) + + +################################################################################ +# Python jitter Core # +################################################################################ + + class JitCore_Python(jitcore.JitCore): "JiT management, using Miasm2 Symbol Execution engine as backend" @@ -15,7 +57,7 @@ class JitCore_Python(jitcore.JitCore): "Preload symbols according to current architecture" symbols_init = {} - for i, r in enumerate(arch.regs.all_regs_ids): + for i, r in enumerate(arch.regs.all_regs_ids_no_alias): symbols_init[r] = arch.regs.all_regs_ids_init[i] self.symbexec = symbexec(arch, symbols_init, @@ -72,6 +114,9 @@ class JitCore_Python(jitcore.JitCore): cur_label = label loop = True + # Required to detect new instructions + offsets_jitted = set() + # Get exec engine exec_engine = self.symbexec @@ -89,29 +134,33 @@ class JitCore_Python(jitcore.JitCore): assert(loop is not False) # Refresh CPU values according to @cpu instance - for symbol in exec_engine.symbols: - if isinstance(symbol, m2_expr.ExprId): - if hasattr(cpu, symbol.name): - value = m2_expr.ExprInt_fromsize(symbol.size, - getattr(cpu, symbol.name)) - exec_engine.symbols.symbols_id[symbol] = value - else: - raise NotImplementedError("Type not handled: %s" % symbol) + update_engine_from_cpu(cpu, exec_engine) # Execute current ir bloc - ad = expr_simp(exec_engine.emulbloc(irb)) + for ir, line in zip(irb.irs, irb.lines): + + # For each new instruction (in assembly) + if line.offset not in offsets_jitted: + offsets_jitted.add(line.offset) + + # Check for memory exception + if (vmmngr.vm_get_exception() != 0): + update_cpu_from_engine(cpu, exec_engine) + return line.offset + + # Eval current instruction (in IR) + exec_engine.eval_ir(ir) + + # Check for memory exception which do not update PC + if (vmmngr.vm_get_exception() & csts.EXCEPT_DO_NOT_UPDATE_PC != 0): + update_cpu_from_engine(cpu, exec_engine) + return line.offset + + # Get next bloc address + ad = expr_simp(exec_engine.eval_expr(irb.dst)) # Updates @cpu instance according to new CPU values - for symbol in exec_engine.symbols: - if isinstance(symbol, m2_expr.ExprId): - if hasattr(cpu, symbol.name): - value = exec_engine.symbols.symbols_id[symbol] - if not isinstance(value, m2_expr.ExprInt): - raise ValueError("A simplification is missing: %s" % value) - - setattr(cpu, symbol.name, value.arg.arg) - else: - raise NotImplementedError("Type not handled: %s" % symbol) + update_cpu_from_engine(cpu, exec_engine) # Manage resulting address if isinstance(ad, m2_expr.ExprInt): diff --git a/miasm2/jitter/vm_mngr_py.c b/miasm2/jitter/vm_mngr_py.c index a99890fd..19686930 100644 --- a/miasm2/jitter/vm_mngr_py.c +++ b/miasm2/jitter/vm_mngr_py.c @@ -163,9 +163,6 @@ PyObject* vm_set_mem(VmMngr* self, PyObject* args) Py_ssize_t length; int ret = 0x1337; uint64_t val; - uint64_t l; - - struct memory_page_node * mpn; if (!PyArg_ParseTuple(args, "OO", &addr, &item_str)) return NULL; @@ -178,18 +175,12 @@ PyObject* vm_set_mem(VmMngr* self, PyObject* args) buf_size = PyString_Size(item_str); PyString_AsStringAndSize(item_str, &buf_data, &length); - /* read is multiple page wide */ + /* write is multiple page wide */ while (buf_size){ - mpn = get_memory_page_from_address(&self->vm_mngr, val); - if (!mpn){ - PyErr_SetString(PyExc_RuntimeError, "cannot find address"); - return 0; - } - l = MIN(buf_size, mpn->size - (val-mpn->ad)); - memcpy(mpn->ad_hp + (val-mpn->ad), buf_data, l); - buf_data += l; - val += l; - buf_size -= l; + MEM_WRITE_08(&self->vm_mngr, val, (char) *(buf_data)); + buf_data += 1; + val += 1; + buf_size -= 1; } return PyLong_FromUnsignedLongLong((uint64_t)ret); diff --git a/test/test_all.py b/test/test_all.py index 55511a84..d822b244 100644 --- a/test/test_all.py +++ b/test/test_all.py @@ -5,6 +5,18 @@ import time import argparse import tempfile +# Test derivations +def all_jit(assembly_line): + """Add all available jitter options to assembly_line thanks to '--jitter' + option. + @assembly_line: list(str) + Return a list of assembly lines: list(list(str)). + """ + out = [] + for jitter in ["tcc", "llvm", "python"]: + out.append(assembly_line + ["--jitter", jitter]) + return out + # Available tests all_tests = { @@ -67,31 +79,17 @@ all_tests = { ["expression/solve_condition_stp.py", "expression/simple_test.bin"], ], - "jitter": [ - ["unpack_upx.py", "--jitter", "tcc", "box_upx.exe"], - ["unpack_upx.py", "--jitter", "llvm", "box_upx.exe"], - ["test_jit_x86_32.py", "--jitter", "tcc", "x86_32_sc.bin"], - ["test_jit_x86_32.py", "--jitter", "llvm", "x86_32_sc.bin"], - ["test_jit_x86_32.py", "--jitter", "python", "x86_32_sc.bin"], - ["test_jit_arm.py", "--jitter", "tcc","md5_arm", "A684"], - ["test_jit_arm.py", "--jitter", "llvm","md5_arm", "A684"], - ["test_jit_arm.py", "--jitter", "python","md5_arm", "A684"], - ["sandbox_pe_x86_32.py", "--jitter", "tcc", "box_x86_32.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "llvm", "box_x86_32.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "python", "box_x86_32.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "tcc", "box_x86_32_enc.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "llvm", "box_x86_32_enc.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "tcc", "box_x86_32_mod.bin"], - ["sandbox_pe_x86_32.py", "--jitter", "llvm", "box_x86_32_mod.bin"], - ["sandbox_pe_x86_32.py", "--jitter", - "tcc", "box_x86_32_mod_self.bin"], - ["sandbox_pe_x86_32.py", "--jitter", - "llvm", "box_x86_32_mod_self.bin"], - ["sandbox_pe_x86_32.py", "--jitter", - "tcc", "box_x86_32_repmod.bin"], - ["sandbox_pe_x86_32.py", "--jitter", - "llvm", "box_x86_32_repmod.bin"], - ], + "jitter": reduce(lambda x, y: x + y, + map(all_jit, [ + ["unpack_upx.py", "box_upx.exe"], # Take 5 mins on a Core i5 + ["test_jit_x86_32.py", "x86_32_sc.bin"], + ["test_jit_arm.py", "md5_arm", "A684"], + ["sandbox_pe_x86_32.py", "box_x86_32.bin"], + ["sandbox_pe_x86_32.py", "box_x86_32_enc.bin"], + ["sandbox_pe_x86_32.py", "box_x86_32_mod.bin"], + ["sandbox_pe_x86_32.py", "box_x86_32_repmod.bin"], + ["sandbox_pe_x86_32.py", "box_x86_32_mod_self.bin"], + ])), "order": [ "assembler", "expression", |