Miasm2
 All Classes Namespaces Files Functions Variables Typedefs Properties Macros
sem.py
Go to the documentation of this file.
1 #!/usr/bin/env python
2 #-*- coding:utf-8 -*-
3 
5 from miasm2.arch.msp430.regs import *
6 from miasm2.arch.msp430.arch import mn_msp430
7 from miasm2.ir.ir import ir
8 
9 
10 # Utils
11 def hex2bcd(val):
12  "Return val as BCD"
13  try:
14  return int("%x" % val, 10)
15  except ValueError:
16  raise NotImplementedError("Not defined behaviour")
17 
18 
19 def bcd2hex(val):
20  "Return the hex value of a BCD"
21  try:
22  return int("0x%d" % val, 16)
23  except ValueError:
24  raise NotImplementedError("Not defined behaviour")
25 
26 
28  return [ExprAff(res, ExprInt(0, 7))]
29 
30 
32  return [ExprAff(zf, ExprCond(a, ExprInt_from(zf, 0), ExprInt_from(zf, 1)))]
33 
34 
36  return [ExprAff(nf, a.msb())]
37 
38 
40  return [ExprAff(pf, ExprOp('parity', a & ExprInt_from(a, 0xFF)))]
41 
42 
44  return [ExprAff(cf, ExprCond(a, ExprInt_from(cf, 1), ExprInt_from(cf, 0)))]
45 
46 
48  e = []
49  e += update_flag_zf(a)
50  e += update_flag_nf(a)
51  e += reset_sr_res()
52  return e
53 
54 
55 def update_flag_sub_cf(a, b, c):
56  return [ExprAff(cf,
57  ((((a ^ b) ^ c) ^ ((a ^ c) & (a ^ b))).msb()) ^ ExprInt1(1))]
58 
59 
60 def update_flag_add_cf(a, b, c):
61  return [ExprAff(cf, (((a ^ b) ^ c) ^ ((a ^ c) & (~(a ^ b)))).msb())]
62 
63 
64 def update_flag_add_of(a, b, c):
65  return [ExprAff(of, (((a ^ c) & (~(a ^ b)))).msb())]
66 
67 
68 def update_flag_sub_of(a, b, c):
69  return [ExprAff(of, (((a ^ c) & (a ^ b))).msb())]
70 
71 
72 def mng_autoinc(a, b, size):
73  e = []
74  if not (isinstance(a, ExprOp) and a.op == "autoinc"):
75  return e, a, b
76 
77  a_r = a.args[0]
78  e.append(ExprAff(a_r, a_r + ExprInt_from(a_r, size / 8)))
79  a = ExprMem(a_r, size)
80  if isinstance(b, ExprMem) and a_r in b.arg:
81  b = ExprMem(b.arg + ExprInt16(size / 8), b.size)
82  return e, a, b
83 
84 # Mnemonics
85 
86 
87 def mov_b(ir, instr, a, b):
88  e, a, b = mng_autoinc(a, b, 8)
89  if isinstance(b, ExprMem):
90  b = ExprMem(b.arg, 8)
91  a = a[:8]
92  else:
93  a = a[:8].zeroExtend(16)
94  e.append(ExprAff(b, a))
95  return e, []
96 
97 
98 def mov_w(ir, instr, a, b):
99  e, a, b = mng_autoinc(a, b, 16)
100  e.append(ExprAff(b, a))
101  if b == ir.pc:
102  e.append(ExprAff(ir.IRDst, a))
103  return e, []
104 
105 
106 def and_b(ir, instr, a, b):
107  e, a, b = mng_autoinc(a, b, 8)
108  c = a[:8] & b[:8]
109  e.append(ExprAff(b, c.zeroExtend(16)))
110  e += update_flag_zn_r(c)
111  e += update_flag_cf_inv_zf(c)
112  e += [ExprAff(of, ExprInt1(0))]
113  return e, []
114 
115 
116 def and_w(ir, instr, a, b):
117  e, a, b = mng_autoinc(a, b, 16)
118  c = a & b
119  e.append(ExprAff(b, c))
120  e += update_flag_zn_r(c)
121  e += update_flag_cf_inv_zf(c)
122  e += [ExprAff(of, ExprInt1(0))]
123  return e, []
124 
125 
126 def bic_b(ir, instr, a, b):
127  e, a, b = mng_autoinc(a, b, 8)
128  c = (a[:8] ^ ExprInt8(0xff)) & b[:8]
129  c = c.zeroExtend(b.size)
130  e.append(ExprAff(b, c))
131  return e, []
132 
133 
134 def bic_w(ir, instr, a, b):
135  e, a, b = mng_autoinc(a, b, 16)
136  c = (a ^ ExprInt16(0xffff)) & b
137  e.append(ExprAff(b, c))
138  return e, []
139 
140 
141 def bis_w(ir, instr, a, b):
142  e, a, b = mng_autoinc(a, b, 16)
143  c = a | b
144  e.append(ExprAff(b, c))
145  return e, []
146 
147 
148 def bit_w(ir, instr, a, b):
149  e, a, b = mng_autoinc(a, b, 16)
150  c = a & b
151  e += update_flag_zn_r(c)
152  e += update_flag_cf_inv_zf(c)
153  e.append(ExprAff(of, ExprInt1(0)))
154  return e, []
155 
156 """
157 def sub_b(ir, instr, a, b):
158  e, a, b = mng_autoinc(a, b, 8)
159  c = b - a
160  e.append(ExprAff(b, c))
161  e += update_flag_zn_r(c)
162  e += update_flag_sub_cf(b, a, c)
163  return None, e, []
164 """
165 
166 
167 def sub_w(ir, instr, a, b):
168  e, a, b = mng_autoinc(a, b, 16)
169  c = b - a
170  e.append(ExprAff(b, c))
171  e += update_flag_zn_r(c)
172  e += update_flag_sub_cf(b, a, c)
173  # micrcorruption
174  # e += update_flag_sub_of(a, b, c)
175  # e += update_flag_sub_of(b, a, c)
176  return e, []
177 
178 
179 def add_b(ir, instr, a, b):
180  e, a, b = mng_autoinc(a, b, 8)
181  if isinstance(b, ExprMem):
182  b = ExprMem(b.arg, 8)
183  else:
184  b = b[:8]
185  a = a[:8]
186  c = b + a
187  e.append(ExprAff(b, c))
188  e += update_flag_zn_r(c)
189  e += update_flag_add_cf(a, b, c)
190  e += update_flag_add_of(a, b, c)
191  return e, []
192 
193 
194 def add_w(ir, instr, a, b):
195  e, a, b = mng_autoinc(a, b, 16)
196  c = b + a
197  e.append(ExprAff(b, c))
198  e += update_flag_zn_r(c)
199  e += update_flag_add_cf(a, b, c)
200  e += update_flag_add_of(a, b, c)
201  return e, []
202 
203 
204 def dadd_w(ir, instr, a, b):
205  e, a, b = mng_autoinc(a, b, 16)
206  # TODO: microcorruption no carryflag
207  c = ExprOp("bcdadd", b, a) # +zeroExtend(cf, 16))
208 
209  e.append(ExprAff(b, c))
210  # e += update_flag_zn_r(c)
211 
212  # micrcorruption
213  e += update_flag_zf(a)
214  # e += update_flag_nf(a)
215  e += reset_sr_res()
216 
217  e.append(ExprAff(cf, ExprOp("bcdadd_cf", b, a))) # +zeroExtend(cf, 16))))
218 
219  # of : undefined
220  return e, []
221 
222 
223 def xor_w(ir, instr, a, b):
224  e, a, b = mng_autoinc(a, b, 16)
225  c = b ^ a
226  e.append(ExprAff(b, c))
227  e += update_flag_zn_r(c)
228  e += update_flag_cf_inv_zf(c)
229  e.append(ExprAff(of, b.msb() & a.msb()))
230  return e, []
231 
232 
233 def push_w(ir, instr, a):
234  e = []
235  e.append(ExprAff(ExprMem(SP - ExprInt16(2), 16), a))
236  e.append(ExprAff(SP, SP - ExprInt16(2)))
237  return e, []
238 
239 
240 def call(ir, instr, a):
241  e, a, dummy = mng_autoinc(a, None, 16)
242  n = ExprId(ir.get_next_label(instr), 16)
243  e.append(ExprAff(ExprMem(SP - ExprInt16(2), 16), n))
244  e.append(ExprAff(SP, SP - ExprInt16(2)))
245  e.append(ExprAff(PC, a))
246  e.append(ExprAff(ir.IRDst, a))
247  return e, []
248 
249 
250 def swpb(ir, instr, a):
251  e = []
252  x, y = a[:8], a[8:16]
253  e.append(ExprAff(a, ExprCompose([(y, 0, 8),
254  (x, 8, 16)])))
255  return e, []
256 
257 
258 def cmp_w(ir, instr, a, b):
259  e, a, b = mng_autoinc(a, b, 16)
260  c = b - a
261  e += update_flag_zn_r(c)
262  e += update_flag_sub_cf(b, a, c)
263  e += update_flag_sub_of(b, a, c)
264  return e, []
265 
266 
267 def cmp_b(ir, instr, a, b):
268  e, a, b = mng_autoinc(a, b, 8)
269  c = b[:8] - a[:8]
270  e += update_flag_zn_r(c)
271  e += update_flag_sub_cf(b[:8], a[:8], c)
272  e += update_flag_sub_of(b[:8], a[:8], c)
273  return e, []
274 
275 
276 def jz(ir, instr, a):
277  n = ExprId(ir.get_next_label(instr), 16)
278  e = []
279  e.append(ExprAff(PC, ExprCond(zf, a, n)))
280  e.append(ExprAff(ir.IRDst, ExprCond(zf, a, n)))
281  return e, []
282 
283 
284 def jnz(ir, instr, a):
285  n = ExprId(ir.get_next_label(instr), 16)
286  e = []
287  e.append(ExprAff(PC, ExprCond(zf, n, a)))
288  e.append(ExprAff(ir.IRDst, ExprCond(zf, n, a)))
289  return e, []
290 
291 
292 def jl(ir, instr, a):
293  n = ExprId(ir.get_next_label(instr), 16)
294  e = []
295  e.append(ExprAff(PC, ExprCond(nf ^ of, a, n)))
296  e.append(ExprAff(ir.IRDst, ExprCond(nf ^ of, a, n)))
297  return e, []
298 
299 
300 def jc(ir, instr, a):
301  n = ExprId(ir.get_next_label(instr), 16)
302  e = []
303  e.append(ExprAff(PC, ExprCond(cf, a, n)))
304  e.append(ExprAff(ir.IRDst, ExprCond(cf, a, n)))
305  return e, []
306 
307 
308 def jnc(ir, instr, a):
309  n = ExprId(ir.get_next_label(instr), 16)
310  e = []
311  e.append(ExprAff(PC, ExprCond(cf, n, a)))
312  e.append(ExprAff(ir.IRDst, ExprCond(cf, n, a)))
313  return e, []
314 
315 
316 def jge(ir, instr, a):
317  n = ExprId(ir.get_next_label(instr), 16)
318  e = []
319  e.append(ExprAff(PC, ExprCond(nf ^ of, n, a)))
320  e.append(ExprAff(ir.IRDst, ExprCond(nf ^ of, n, a)))
321  return e, []
322 
323 
324 def jmp(ir, instr, a):
325  e = []
326  e.append(ExprAff(PC, a))
327  e.append(ExprAff(ir.IRDst, a))
328  return e, []
329 
330 
331 def rrc_w(ir, instr, a):
332  e = []
333  c = ExprCompose([(a[1:16], 0, 15),
334  (cf, 15, 16)])
335  e.append(ExprAff(a, c))
336  e.append(ExprAff(cf, a[:1]))
337  # e += update_flag_zn_r(c)
338 
339  # micrcorruption
340  e += update_flag_zf(a)
341  # e += update_flag_nf(a)
342  e += reset_sr_res()
343 
344  e.append(ExprAff(of, ExprInt1(0)))
345  return e, []
346 
347 
348 def rra_w(ir, instr, a):
349  e = []
350  c = ExprCompose([(a[1:16], 0, 15),
351  (a[15:16], 15, 16)])
352  e.append(ExprAff(a, c))
353  # TODO: error in disasm microcorruption?
354  # e.append(ExprAff(cf, a[:1]))
355  # e += update_flag_zn_r(c)
356 
357  # micrcorruption
358  e += update_flag_zf(a)
359  # e += update_flag_nf(a)
360  e += reset_sr_res()
361 
362  e.append(ExprAff(of, ExprInt1(0)))
363  return e, []
364 
365 
366 def sxt(ir, instr, a):
367  e = []
368  c = a[:8].signExtend(16)
369  e.append(ExprAff(a, c))
370 
371  e += update_flag_zn_r(c)
372  e += update_flag_cf_inv_zf(c)
373  e.append(ExprAff(of, ExprInt1(0)))
374 
375  return e, []
376 
377 mnemo_func = {
378  "mov.b": mov_b,
379  "mov.w": mov_w,
380  "and.b": and_b,
381  "and.w": and_w,
382  "bic.b": bic_b,
383  "bic.w": bic_w,
384  "bis.w": bis_w,
385  "bit.w": bit_w,
386  "sub.w": sub_w,
387  "add.b": add_b,
388  "add.w": add_w,
389  "push.w": push_w,
390  "dadd.w": dadd_w,
391  "xor.w": xor_w,
392  "call": call,
393  "swpb": swpb,
394  "cmp.w": cmp_w,
395  "cmp.b": cmp_b,
396  "jz": jz,
397  "jnz": jnz,
398  "jl": jl,
399  "jc": jc,
400  "jnc": jnc,
401  "jmp": jmp,
402  "jge": jge,
403  "rrc.w": rrc_w,
404  "rra.w": rra_w,
405  "sxt": sxt,
406 }
407 
408 
409 composed_sr = ExprCompose([
410  (cf, 0, 1),
411  (zf, 1, 2),
412  (nf, 2, 3),
413  (gie, 3, 4),
414  (cpuoff, 4, 5),
415  (osc, 5, 6),
416  (scg0, 6, 7),
417  (scg1, 7, 8),
418  (of, 8, 9),
419  (res, 9, 16),
420 ])
421 
422 
423 def ComposeExprAff(dst, src):
424  e = []
425  for x, start, stop in dst.args:
426  e.append(ExprAff(x, src[start:stop]))
427  return e
428 
429 
430 class ir_msp430(ir):
431 
432  def __init__(self, symbol_pool=None):
433  ir.__init__(self, mn_msp430, None, symbol_pool)
434  self.pc = PC
435  self.sp = SP
436  self.IRDst = ExprId('IRDst', 16)
437 
438  def mod_pc(self, instr, instr_ir, extra_ir):
439  pass
440 
441  def get_ir(self, instr):
442  # print instr#, args
443  args = instr.args
444  instr_ir, extra_ir = mnemo_func[instr.name](self, instr, *args)
445  self.mod_sr(instr, instr_ir, extra_ir)
446 
447  return instr_ir, extra_ir
448 
449  def mod_sr(self, instr, instr_ir, extra_ir):
450  for i, x in enumerate(instr_ir):
451  x = ExprAff(x.dst, x.src.replace_expr({SR: composed_sr}))
452  instr_ir[i] = x
453  if x.dst != SR:
454  continue
455  xx = ComposeExprAff(composed_sr, x.src)
456  instr_ir[i:i+1] = xx
457  for i, x in enumerate(instr_ir):
458  x = ExprAff(x.dst, x.src.replace_expr(
459  {self.pc: ExprInt16(instr.offset + instr.l)}))
460  instr_ir[i] = x
461 
462  if extra_ir:
463  raise NotImplementedError('not fully functional')
def update_flag_cf_inv_zf
Definition: sem.py:43
def update_flag_zn_r
Definition: sem.py:47
def update_flag_add_of
Definition: sem.py:64
def update_flag_add_cf
Definition: sem.py:60
def update_flag_sub_of
Definition: sem.py:68
def update_flag_sub_cf
Definition: sem.py:55