Mercurial > lcfOS
comparison python/x86.py @ 177:460db5669efa
Added clean pass for IR
author | Windel Bouwman |
---|---|
date | Mon, 22 Apr 2013 23:54:54 +0200 |
parents | 3eb06f5fb987 |
children | c694ec551f34 |
comparison
equal
deleted
inserted
replaced
176:5fd02aa38b42 | 177:460db5669efa |
---|---|
1 import ppci | 1 import ppci |
2 import ir | 2 import ir |
3 import registerallocator | 3 import registerallocator |
4 | 4 |
5 # Instruction selection with DAG (Directed Acyclic Graph) | |
6 class DagLeaf: | |
7 def __init__(self, v): | |
8 self.v = v | |
9 | |
10 class DagNode: | |
11 def __init__(self, name): | |
12 self.name = name | |
13 self.children = [] | |
14 def __repr__(self): | |
15 return str(self.name) | |
16 | |
17 class Dag: | |
18 def __init__(self, bb): | |
19 self.mapping = {} | |
20 self.buildFromBB(bb) | |
21 def buildFromBB(self, bb): | |
22 for ins in bb.Instructions: | |
23 if type(ins) is ir.BinaryOperator: | |
24 if not ins.value1 in self.mapping: | |
25 self.mapping[ins.value1] = DagNode(ins.value1) | |
26 if not ins.value2 in self.mapping: | |
27 self.mapping[ins.value2] = DagNode(ins.value2) | |
28 # look for op with left and right operand the same: | |
29 N = None | |
30 lnode = self.mapping[ins.value1] | |
31 rnode = self.mapping[ins.value2] | |
32 for node in self.mapping.values(): | |
33 if node.name == ins.operation: | |
34 if node.children[0] == lnode and node.children[1] == rnode: | |
35 N = node | |
36 break | |
37 if not N: | |
38 # Create a node. | |
39 N = DagNode(ins.operation) | |
40 N.children.append(lnode) | |
41 N.children.append(rnode) | |
42 self.mapping[ins.result] = N | |
43 else: | |
44 pass | |
45 def dumpgv(self, outf): | |
46 outf.write('subgraph {0} {{\n'.format(id(self))) | |
47 for node in self.mapping.values(): | |
48 outf.write('{0} [label="{1}"];\n'.format(id(node), node.name)) | |
49 for c in node.children: | |
50 outf.write('{0} -> {1};\n'.format(id(node), id(c))) | |
51 outf.write('label="dag"}\n') | |
52 | |
53 def insSelect(mod): | |
54 """ Create DAG from ir-code """ | |
55 for bb in mod.BasicBlocks: | |
56 print(bb) | |
57 dag = Dag(bb) | |
58 print(dag.mapping) | |
59 bb.dag = dag | |
60 | |
61 # x86 specific: | |
5 class AsmLabel: | 62 class AsmLabel: |
6 def __init__(self, lab): | 63 def __init__(self, lab): |
7 self.lab = lab | 64 self.lab = lab |
8 def __repr__(self): | 65 def __repr__(self): |
9 return '{0}:'.format(self.lab) | 66 return '{0}:'.format(self.lab) |
32 self.asm.append(i) | 89 self.asm.append(i) |
33 | 90 |
34 def genBin(self, ir): | 91 def genBin(self, ir): |
35 self.asm = [] | 92 self.asm = [] |
36 # Allocate registers: | 93 # Allocate registers: |
94 insSelect(ir) | |
37 ra = registerallocator.RegisterAllocator() | 95 ra = registerallocator.RegisterAllocator() |
38 # TODO: do not register allocate on intermediate code: | 96 # TODO: do not register allocate on intermediate code: |
39 ra.registerAllocate(ir, self.regs) | 97 ra.registerAllocate(ir, self.regs) |
40 self.genModule(ir) | 98 self.genModule(ir) |
41 return self.asm | 99 return self.asm |