Mercurial > lcfOS
comparison python/c3/codegenerator.py @ 158:9683a4cd848f
Added some functions for code generation
author | Windel Bouwman |
---|---|
date | Fri, 08 Mar 2013 16:52:44 +0100 |
parents | 8f3924b6076e |
children | 0b5b2ee6b435 |
comparison
equal
deleted
inserted
replaced
157:8f3924b6076e | 158:9683a4cd848f |
---|---|
18 m.Globals.append(v) | 18 m.Globals.append(v) |
19 | 19 |
20 def genFunction(m, fnc): | 20 def genFunction(m, fnc): |
21 ft = genType(fnc.typ) | 21 ft = genType(fnc.typ) |
22 f = ir.Function(fnc.name, ft) | 22 f = ir.Function(fnc.name, ft) |
23 m.Globals.append(f) | 23 m.Functions.append(f) |
24 bb = ir.BasicBlock() | 24 bb = ir.BasicBlock() |
25 f.BasicBlocks.append(bb) | 25 f.BasicBlocks.append(bb) |
26 genCode(bb, fnc.body) | 26 genCode(bb, fnc.body) |
27 bb.Instructions.append(ir.RetInstruction()) | |
27 | 28 |
28 def genCode(bb, code): | 29 def genCode(bb, code): |
29 if type(code) is astnodes.CompoundStatement: | 30 if type(code) is astnodes.CompoundStatement: |
30 for s in code.statements: | 31 for s in code.statements: |
31 genCode(bb, s) | 32 genCode(bb, s) |
32 elif type(code) is astnodes.Assignment: | 33 elif type(code) is astnodes.Assignment: |
33 genCode(bb, code.rval) | 34 genExprCode(bb, code.rval) |
34 print('assign') | 35 # TODO: store |
35 elif type(code) is astnodes.IfStatement: | 36 elif type(code) is astnodes.IfStatement: |
36 genCode(bb, code.condition) | 37 genExprCode(bb, code.condition) |
38 # TODO: implement IF. | |
39 t1, t2 = 1,2 | |
40 b = ir.BranchInstruction(t1, t2) | |
41 bb.Instructions.append(b) | |
37 genCode(bb, code.truestatement) | 42 genCode(bb, code.truestatement) |
38 print('If!') | 43 genCode(bb, code.falsestatement) |
39 elif type(code) is astnodes.Binop: | 44 elif type(code) is astnodes.ProcedureCall: |
40 genCode(bb, code.a) | 45 ins = ir.CallInstruction('f', []) |
41 genCode(bb, code.b) | 46 bb.Instructions.append(ins) |
42 a = 1 | 47 elif type(code) is astnodes.EmptyStatement: |
43 b = 2 | 48 pass |
44 if code.op == '+': | 49 elif type(code) is astnodes.ReturnStatement: |
45 bb.Instructions.append(ir.AddInstruction(a, b)) | 50 bb.Instructions.append(ir.RetInstruction()) |
51 else: | |
52 print('Unknown stmt:', code) | |
53 | |
54 def NumGen(): | |
55 a = 0 | |
56 while True: | |
57 yield a | |
58 a = a + 1 | |
59 | |
60 nums = NumGen() | |
61 def unique(): | |
62 return 'tmp{0}'.format(nums.__next__()) | |
63 | |
64 def genExprCode(bb, code): | |
65 if type(code) is astnodes.Binop: | |
66 a = genExprCode(bb, code.a) | |
67 b = genExprCode(bb, code.b) | |
68 ops = {'+': 'fadd', '-': 'fsub', '*':'fmul', '/':'fdiv'} | |
69 if code.op in ops: | |
70 op = ops[code.op] | |
71 tmp = unique() | |
72 ins = ir.BinaryOperator(tmp, op, a, b) | |
73 bb.Instructions.append(ins) | |
74 return tmp | |
46 else: | 75 else: |
47 bb.Instructions.append(ir.BinaryOperator(code.op, a, b)) | 76 print('Unknown binop') |
77 bb.Instructions.append(ir.BinaryOperator('unk2', code.op, a, b)) | |
78 return 'unk2' | |
48 elif type(code) is astnodes.Constant: | 79 elif type(code) is astnodes.Constant: |
49 print('CST') | 80 tmp = unique() |
50 bb.Instructions.append(ir.ImmLoadInstruction(code.value)) | 81 bb.Instructions.append(ir.LoadInstruction(tmp, code.value)) |
82 return tmp | |
83 elif type(code) is astnodes.VariableUse: | |
84 tmp = unique() | |
85 ins = ir.LoadInstruction(tmp, code.target.name) | |
86 return tmp | |
51 else: | 87 else: |
52 print('Unknown:', code) | 88 print('Unknown expr:', code) |
89 return 'unk' | |
53 | 90 |
54 def genType(t): | 91 def genType(t): |
55 return ir.Type() | 92 return ir.Type() |
56 | 93 |
57 class CodeGenerator: | 94 class CodeGenerator: |