comparison python/ppci/irutils.py @ 307:e609d5296ee9

Massive rewrite of codegenerator
author Windel Bouwman
date Thu, 12 Dec 2013 20:42:56 +0100
parents
children 68b01c8abf8a
comparison
equal deleted inserted replaced
306:b145f8e6050b 307:e609d5296ee9
1
2 """
3 Some utilities for ir-code.
4 """
5 from .ir import Temp, Block, Function, Statement
6
7 def dumpgv(m, outf):
8 print('digraph G ', file=outf)
9 print('{', file=outf)
10 for f in m.Functions:
11 print('{} [label="{}" shape=box3d]'.format(id(f), f), file=outf)
12 for bb in f.Blocks:
13 contents = str(bb) + '\n'
14 contents += '\n'.join([str(i) for i in bb.Instructions])
15 print('{0} [shape=note label="{1}"];'
16 .format(id(bb), contents), file=outf)
17 for successor in bb.Successors:
18 print('"{}" -> "{}"'.format(id(bb), id(successor)), file=outf)
19
20 print('"{}" -> "{}" [label="entry"]'
21 .format(id(f), id(f.entry)), file=outf)
22 print('}', file=outf)
23
24
25 # Constructing IR:
26
27 class NamedClassGenerator:
28 def __init__(self, prefix, cls):
29 self.prefix = prefix
30 self.cls = cls
31
32 def NumGen():
33 a = 0
34 while True:
35 yield a
36 a = a + 1
37 self.nums = NumGen()
38
39 def gen(self, prefix=None):
40 if not prefix:
41 prefix = self.prefix
42 return self.cls('{0}{1}'.format(prefix, self.nums.__next__()))
43
44
45 class Builder:
46 """ Base class for ir code generators """
47 def __init__(self):
48 self.prepare()
49
50 def prepare(self):
51 self.newTemp = NamedClassGenerator('reg', Temp).gen
52 self.newBlock2 = NamedClassGenerator('block', Block).gen
53 self.bb = None
54 self.m = None
55 self.fn = None
56 self.loc = None
57
58 # Helpers:
59 def setModule(self, m):
60 self.m = m
61
62 def newFunction(self, name):
63 f = Function(name)
64 self.m.addFunc(f)
65 return f
66
67 def newBlock(self):
68 assert self.fn
69 b = self.newBlock2()
70 b.function = self.fn
71 return b
72
73 def setFunction(self, f):
74 self.fn = f
75 self.bb = f.entry if f else None
76
77 def setBlock(self, b):
78 self.bb = b
79
80 def setLoc(self, l):
81 self.loc = l
82
83 def emit(self, i):
84 assert isinstance(i, Statement)
85 i.debugLoc = self.loc
86 if not self.bb:
87 raise Exception('No basic block')
88 self.bb.addInstruction(i)