about summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--example/expression/constant_propagation.py54
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_1.S21
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_10.S17
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_11.S11
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_12.S12
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_13.S7
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_14.S10
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_15.S16
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_16.S17
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_17.S8
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_18.S33
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_19.S16
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_2.S21
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_20.S19
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_3.S15
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_4.S15
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_5.S24
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_6.S37
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_7.S16
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_8.S18
-rw-r--r--test/samples/x86_32/cst_propag/x86_32_sc_9.S36
-rwxr-xr-xtest/test_all.py21
22 files changed, 442 insertions, 2 deletions
diff --git a/example/expression/constant_propagation.py b/example/expression/constant_propagation.py
new file mode 100644
index 00000000..70394580
--- /dev/null
+++ b/example/expression/constant_propagation.py
@@ -0,0 +1,54 @@
+"""
+Example of "constant expression" propagation.
+A "constant expression" is an expression based on constants or init regs.
+
+"""
+
+from argparse import ArgumentParser
+
+from miasm2.arch.x86.disasm import dis_x86_32 as dis_engine
+from miasm2.analysis.machine import Machine
+from miasm2.analysis.binary import Container
+from miasm2.analysis.cst_propag import propagate_cst_expr
+from miasm2.analysis.data_flow import dead_simp
+from miasm2.expression.simplifications import expr_simp
+
+
+parser = ArgumentParser("Constant expression propagation")
+parser.add_argument('filename', help="File to analyze")
+parser.add_argument('address', help="Starting address for disassembly engine")
+parser.add_argument('-s', "--simplify", action="store_true",
+                    help="Apply simplifications rules (liveness, graph simplification, ...)")
+
+args = parser.parse_args()
+
+
+machine = Machine("x86_32")
+
+cont = Container.from_stream(open(args.filename))
+ira, dis_engine = machine.ira, machine.dis_engine
+mdis = dis_engine(cont.bin_stream)
+ir_arch = ira(mdis.symbol_pool)
+addr = int(args.address, 0)
+
+
+blocks = mdis.dis_multiblock(addr)
+for block in blocks:
+    ir_arch.add_block(block)
+
+
+init_infos = ir_arch.arch.regs.regs_init
+cst_propag_link = propagate_cst_expr(ir_arch, addr, init_infos)
+
+if args.simplify:
+    ir_arch.simplify(expr_simp)
+    modified = True
+    while modified:
+        modified = False
+        modified |= dead_simp(ir_arch)
+        modified |= ir_arch.remove_empty_assignblks()
+        modified |= ir_arch.remove_jmp_blocks()
+        modified |= ir_arch.merge_blocks()
+
+
+open("%s.propag.dot" % args.filename, 'w').write(ir_arch.graph.dot())
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_1.S b/test/samples/x86_32/cst_propag/x86_32_sc_1.S
new file mode 100644
index 00000000..0fe12e04
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_1.S
@@ -0,0 +1,21 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, 1
+	MOV         EDX, 2
+	LEA         ECX, DWORD PTR [ECX+0x4]
+	LEA         EBX, DWORD PTR [ECX+0x1]
+	CMP         CL, 0x1
+	JZ          test1
+	LEA         EBX, DWORD PTR [EBX-1]
+	JMP         end
+test1:
+	LEA         EBX, DWORD PTR [EBX-1]
+end:
+	MOV         EAX, EBX
+	LEA         EAX, DWORD PTR [EAX + EDX]
+	MOV         EDX, DWORD PTR [EBP+0xC]
+	LEA         EAX, DWORD PTR [EAX + EDX]
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_10.S b/test/samples/x86_32/cst_propag/x86_32_sc_10.S
new file mode 100644
index 00000000..84eae85b
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_10.S
@@ -0,0 +1,17 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [ESP+0x8]
+	INC         EBX
+	CMP         CL, 0x1
+	JZ          test1
+	MOV         EAX, 8
+	JMP         end
+test1:
+	MOV         EAX, 4
+end:
+	LEA         EBX, DWORD PTR [EAX+EBX]
+	MOV         EAX, EBX
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_11.S b/test/samples/x86_32/cst_propag/x86_32_sc_11.S
new file mode 100644
index 00000000..272c76da
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_11.S
@@ -0,0 +1,11 @@
+main:
+	MOV         ECX, 10
+loop1:
+	DEC         ECX
+	JNZ         less
+	JMP         goon
+less:
+	DEC         ECX
+goon:
+	JNZ         loop1
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_12.S b/test/samples/x86_32/cst_propag/x86_32_sc_12.S
new file mode 100644
index 00000000..3420b882
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_12.S
@@ -0,0 +1,12 @@
+main:
+	MOV         EBX, 1
+	MOV         ECX, 2
+	CMP         EDX, 3
+	JNZ         test1
+	ADD         EBX, 1
+	JMP         goon
+test1:
+	ADD         ECX, 1
+goon:
+	LEA         EAX, DWORD PTR [EBX+ECX]
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_13.S b/test/samples/x86_32/cst_propag/x86_32_sc_13.S
new file mode 100644
index 00000000..08b9a891
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_13.S
@@ -0,0 +1,7 @@
+main:
+	MOV         ECX, 10
+loop:
+	DEC         ECX
+	JNZ         loop
+	MOV         EAX, ECX
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_14.S b/test/samples/x86_32/cst_propag/x86_32_sc_14.S
new file mode 100644
index 00000000..17cad5d7
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_14.S
@@ -0,0 +1,10 @@
+main:
+	MOV         ECX, 10
+	MOV         EDX, 10
+loop:
+	INC         EDX
+	DEC         EDX
+	DEC         ECX
+	JNZ         loop
+	MOV         EAX, EDX
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_15.S b/test/samples/x86_32/cst_propag/x86_32_sc_15.S
new file mode 100644
index 00000000..03a3c121
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_15.S
@@ -0,0 +1,16 @@
+main:
+	ADD         EDI, 1
+	MOV         ECX, 10
+loop1:
+	MOV         EDX, 10
+	INC         EDI
+loop2:
+	ADD         EDI, 2
+	SUB         EDI, 2
+	SUB         EDX, 1
+	JNZ         loop2
+	DEC         EDI
+	SUB         ECX, 1
+	JNZ         loop1
+	MOV         EAX, EDI
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_16.S b/test/samples/x86_32/cst_propag/x86_32_sc_16.S
new file mode 100644
index 00000000..d54e2657
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_16.S
@@ -0,0 +1,17 @@
+main:
+	MOV         EBX, 1
+	ADD         EDI, 1
+	MOV         ECX, 10
+loop1:
+	MOV         EDX, 10
+	INC         EDI
+loop2:
+	LEA         EDI, DWORD PTR [EDI+EBX]
+	LEA         EDI, DWORD PTR [EDI-1]
+	SUB         EDX, 1
+	JNZ         loop2
+	DEC         EDI
+	SUB         ECX, 1
+	JNZ         loop1
+	MOV         EAX, EDI
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_17.S b/test/samples/x86_32/cst_propag/x86_32_sc_17.S
new file mode 100644
index 00000000..576c02e2
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_17.S
@@ -0,0 +1,8 @@
+main:
+	MOV         EBX, 1
+	ADD         EDI, 1
+	SUB         EBX, EDI
+	SUB         EDI, 1
+	ADD         EBX, EDI
+	MOV         EAX, EBX
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_18.S b/test/samples/x86_32/cst_propag/x86_32_sc_18.S
new file mode 100644
index 00000000..7d29abdb
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_18.S
@@ -0,0 +1,33 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         EAX, DWORD PTR [EBP+0x8]
+	MOV         EBX, DWORD PTR [EBP+0xC]
+	ADD         EAX, EBX
+	TEST        EAX, EAX
+	JNZ         test
+	PUSH        1
+	PUSH        2
+	PUSH        DWORD PTR [EBP+0x10]
+	CALL        func1
+	ADD         ESP, 0xC
+	JMP         goon
+test:
+	MOV         ECX, 10
+loop:
+	PUSH        1
+	PUSH        2
+	CALL        func2
+	ADD         ESP, 0x8
+	DEC         ECX
+	JNZ         loop
+goon:
+	MOV         ESP, EBP
+	POP         EBP
+	RET
+
+
+func1:
+	RET
+func2:
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_19.S b/test/samples/x86_32/cst_propag/x86_32_sc_19.S
new file mode 100644
index 00000000..0b0e0837
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_19.S
@@ -0,0 +1,16 @@
+main:
+
+	MOV         EBX, 1
+	MOV         ECX, 1
+	CMP         EDX, 10
+	JZ          test1
+	ADD         EBX, 1
+	ADD         ECX, 1
+	JMP         gogon
+test1:
+	ADD         EBX, 2
+	ADD         ECX, 2
+gogon:
+	ADD         EAX, EBX
+	ADD         EAX, ECX
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_2.S b/test/samples/x86_32/cst_propag/x86_32_sc_2.S
new file mode 100644
index 00000000..96e10fa6
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_2.S
@@ -0,0 +1,21 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [ESP+0x8]
+	MOV         EDX, DWORD PTR [EBP+0xC]
+	LEA         ECX, DWORD PTR [ECX+0x4]
+	LEA         EBX, DWORD PTR [EBX+0x1]
+	CMP         CL, 0x1
+	JZ          test1
+	LEA         EBX, DWORD PTR [EBX-1]
+	JMP         end
+test1:
+	LEA         EBX, DWORD PTR [EBX+0x1]
+end:
+	MOV         EAX, EBX
+	LEA         EAX, DWORD PTR [EAX + EDX]
+	MOV         EDX, DWORD PTR [EBP+0xC]
+	LEA         EAX, DWORD PTR [EAX + EDX]
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_20.S b/test/samples/x86_32/cst_propag/x86_32_sc_20.S
new file mode 100644
index 00000000..4f2b82c6
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_20.S
@@ -0,0 +1,19 @@
+main:
+	MOV         EBX, 0
+	MOV         ECX, 0
+
+	CMP         EDX, 0
+	JNZ         test1
+	JMP         goon
+test1:
+	MOV         EDX, 1
+	LEA         EDX, DWORD PTR [EDX+0xF]
+	LEA         EBX, DWORD PTR [EBX+EDX]
+	MOV         EDX, 2
+	LEA         EDX, DWORD PTR [EDX+0xE]
+	MOV         ECX, EDX
+	LEA         EBX, DWORD PTR [EBX+ECX]
+	JNZ         test1
+goon:
+	MOV         EAX, EBX
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_3.S b/test/samples/x86_32/cst_propag/x86_32_sc_3.S
new file mode 100644
index 00000000..46d2afff
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_3.S
@@ -0,0 +1,15 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+loop:
+	SUB         ECX, 1
+	JZ          end
+	PUSH        EDX
+	POP         ESI
+	JMP         loop
+end:
+	MOV         EAX, DWORD PTR [ESP+0xC]
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_4.S b/test/samples/x86_32/cst_propag/x86_32_sc_4.S
new file mode 100644
index 00000000..1f9e82a3
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_4.S
@@ -0,0 +1,15 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+loop:
+	PUSH        EDX
+	POP         ESI
+	SUB         ECX, 1
+	JZ          end
+	JMP         loop
+end:
+	MOV         EAX, DWORD PTR [ESP+0xC]
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_5.S b/test/samples/x86_32/cst_propag/x86_32_sc_5.S
new file mode 100644
index 00000000..b9d7e08a
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_5.S
@@ -0,0 +1,24 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+
+	SUB         ECX, 1
+	JZ          test1
+	SUB         ECX, 1
+	JZ          test2
+	SUB         ECX, 1
+	JZ          test3
+
+	JMP         end
+test1:
+	INC         EAX
+test2:
+	INC         EAX
+test3:
+	INC         EAX
+end:
+	INC         EAX
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_6.S b/test/samples/x86_32/cst_propag/x86_32_sc_6.S
new file mode 100644
index 00000000..65fc2b8b
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_6.S
@@ -0,0 +1,37 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+
+	INC         EAX
+	SUB         ECX, 1
+	JZ          test1
+	ADD         EAX, 1
+	JMP         go1
+test1:
+	ADD         EAX, 2
+go1:
+
+
+	INC         EAX
+	SUB         ECX, 1
+	JZ          test2
+	ADD         EAX, 0x10
+	JMP         go2
+test2:
+	ADD         EAX, 0x20
+go2:
+
+	INC         EAX
+	SUB         ECX, 1
+	JZ          test3
+	ADD         EAX, 0x30
+	JMP         go3
+test3:
+	ADD         EAX, 0x40
+go3:
+
+	INC         EAX
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_7.S b/test/samples/x86_32/cst_propag/x86_32_sc_7.S
new file mode 100644
index 00000000..96c5fc6e
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_7.S
@@ -0,0 +1,16 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+	INC         EAX
+
+loop:
+	INC         EAX
+	DEC         EAX
+	SUB         ECX, 1
+	JZ          loop
+
+	INC         EAX
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_8.S b/test/samples/x86_32/cst_propag/x86_32_sc_8.S
new file mode 100644
index 00000000..5127c0fa
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_8.S
@@ -0,0 +1,18 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, DWORD PTR [EBP+0x8]
+	INC         EAX
+
+loop:
+	MOV         EDX, 1
+	MOV         ESI, 1
+	ADD         EAX, EDX
+	SUB         EAX, ESI
+	SUB         ECX, 1
+	JZ          loop
+
+	INC         EAX
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/samples/x86_32/cst_propag/x86_32_sc_9.S b/test/samples/x86_32/cst_propag/x86_32_sc_9.S
new file mode 100644
index 00000000..0b01305b
--- /dev/null
+++ b/test/samples/x86_32/cst_propag/x86_32_sc_9.S
@@ -0,0 +1,36 @@
+main:
+	PUSH        EBP
+	MOV         EBP, ESP
+	MOV         ECX, 10 ; DWORD PTR [EBP+0x8]
+
+	MOV         EBX, 0x1000   ;
+	INC         EBX		  ; EBX = 0x1001
+	MOV         EAX, EBX	  ; EAX = 0x1001
+	MOV         EBX, 0x10001  ; EBX = 0x10001
+	DEC         EBX		  ; EBX = 0x10000
+	MOV         ESI, EBX	  ; ESI = 0x10000
+				  ;
+	ADD         EDI, EAX	  ; EDI += 0x1001
+	ADD         EDI, ESI      ; EDI += 0x10000
+	;; EDI = EDI + 0x11001
+
+loop:
+	MOV         EBX, 0x1000   ;
+	MOV         EAX, EBX	  ;
+	MOV         EBX, 0x100001 ;
+	MOV         ESI, EBX	  ;
+	MUL         ESI		  ; EAX = 0x1000
+	MOV         EBX, 0x1	  ;
+	ADD         EDI, EBX	  ; EDI += 1
+	MOV         EBX, 0x1000	  ;
+	ADD         EDI, EBX	  ; EDI += 0x1000
+	SUB         EDI, EAX      ; EDI -= 0x1000
+	DEC         EDI		  ; EDI -= 1
+	SUB         ECX, 1
+	JNZ          loop
+
+	INC         EDI
+	MOV         EAX, EDI
+	MOV         ESP, EBP
+	POP         EBP
+	RET
diff --git a/test/test_all.py b/test/test_all.py
index 07542f6a..17193d9f 100755
--- a/test/test_all.py
+++ b/test/test_all.py
@@ -188,8 +188,9 @@ class SemanticTestAsm(RegressionTest):
         self.command_line = [self.shellcode_script,
                              arch,
                              input_filename,
-                             output_filename,
-                             self.container_dct.get(container, '')]
+                             output_filename]
+        if container in self.container_dct:
+            self.command_line.append(self.container_dct[container])
         self.products = [output_filename, "graph.dot"]
 
 
@@ -304,6 +305,17 @@ testset += RegressionTest(["data_flow.py"], base_dir="analysis",
             for test_nb in xrange(1, 18))
                                     for fname in fnames])
 
+for i in xrange(1, 21):
+    input_name = "cst_propag/x86_32_sc_%d" % i
+    bin_name = "samples/x86_32/%s.bin" % input_name
+    test_x86_32_cst = SemanticTestAsm("x86_32", None, [input_name])
+    testset+= test_x86_32_cst
+    testset += RegressionTest(["../example/expression/constant_propagation.py", "-s", bin_name, "0"],
+                              depends=[test_x86_32_cst],
+                              products=["%s.propag.dot" % bin_name])
+
+
+
 ## Degraph
 class TestDepgraph(RegressionTest):
     """Dependency graph test"""
@@ -565,6 +577,11 @@ testset += ExampleExpression(["access_c.py", Example.get_sample("human.bin")],
 testset += ExampleExpression(["expr_c.py"],
                              tags=[TAGS["cparser"]])
 
+
+testset += ExampleExpression(["constant_propagation.py",
+                              Example.get_sample("simple_test.bin"), "-s", "0"],
+                             products=["%s.propag.dot" % Example.get_sample("simple_test.bin")])
+
 for script in [["basic_op.py"],
                ["basic_simplification.py"],
                ["simplification_tools.py"],