comparison python/ppci/c3/codegenerator.py @ 306:b145f8e6050b

Start on c3 rewrite
author Windel Bouwman
date Mon, 09 Dec 2013 19:00:21 +0100
parents 0615b5308710
children e609d5296ee9
comparison
equal deleted inserted replaced
305:0615b5308710 306:b145f8e6050b
1 import logging 1 import logging
2 from .. import ir 2 from .. import ir
3 from . import astnodes 3 from . import astnodes
4 from .scope import boolType, intType
5 from ppci import CompilerError 4 from ppci import CompilerError
6 from .analyse import theType 5 from .analyse import theType
7 6
8 7
9 class CodeGenerator(ir.Builder): 8 class CodeGenerator(ir.Builder):
41 40
42 def genFunction(self, fn): 41 def genFunction(self, fn):
43 # TODO: handle arguments 42 # TODO: handle arguments
44 f = self.funcMap[fn] 43 f = self.funcMap[fn]
45 f.return_value = self.newTemp() 44 f.return_value = self.newTemp()
46 # TODO reserve room for stack, this can be done at later point?
47 self.setFunction(f) 45 self.setFunction(f)
48 l2 = self.newBlock() 46 l2 = self.newBlock()
49 self.emit(ir.Jump(l2)) 47 self.emit(ir.Jump(l2))
50 self.setBlock(l2) 48 self.setBlock(l2)
51 # generate room for locals: 49 # generate room for locals:
75 assert isinstance(code, astnodes.Statement) 73 assert isinstance(code, astnodes.Statement)
76 self.setLoc(code.loc) 74 self.setLoc(code.loc)
77 if type(code) is astnodes.CompoundStatement: 75 if type(code) is astnodes.CompoundStatement:
78 for s in code.statements: 76 for s in code.statements:
79 self.genCode(s) 77 self.genCode(s)
78 elif type(code) is astnodes.EmptyStatement:
79 pass
80 elif type(code) is astnodes.Assignment: 80 elif type(code) is astnodes.Assignment:
81 rval = self.genExprCode(code.rval) 81 rval = self.genExprCode(code.rval)
82 lval = self.genExprCode(code.lval) 82 lval = self.genExprCode(code.lval)
83 self.emit(ir.Move(lval, rval)) 83 self.emit(ir.Move(lval, rval))
84 elif type(code) is astnodes.ExpressionStatement: 84 elif type(code) is astnodes.ExpressionStatement:
90 self.genCondCode(code.condition, bbtrue, bbfalse) 90 self.genCondCode(code.condition, bbtrue, bbfalse)
91 self.setBlock(bbtrue) 91 self.setBlock(bbtrue)
92 self.genCode(code.truestatement) 92 self.genCode(code.truestatement)
93 self.emit(ir.Jump(te)) 93 self.emit(ir.Jump(te))
94 self.setBlock(bbfalse) 94 self.setBlock(bbfalse)
95 if code.falsestatement: 95 self.genCode(code.falsestatement)
96 self.genCode(code.falsestatement)
97 self.emit(ir.Jump(te)) 96 self.emit(ir.Jump(te))
98 self.setBlock(te) 97 self.setBlock(te)
99 elif type(code) is astnodes.ReturnStatement: 98 elif type(code) is astnodes.ReturnStatement:
100 assert code.expr
101 re = self.genExprCode(code.expr) 99 re = self.genExprCode(code.expr)
102 self.emit(ir.Move(self.fn.return_value, re)) 100 self.emit(ir.Move(self.fn.return_value, re))
103 self.emit(ir.Jump(self.fn.epiloog)) 101 self.emit(ir.Jump(self.fn.epiloog))
104 b = self.newBlock() 102 b = self.newBlock()
105 self.setBlock(b) 103 self.setBlock(b)
117 else: 115 else:
118 raise NotImplementedError('Unknown stmt {}'.format(code)) 116 raise NotImplementedError('Unknown stmt {}'.format(code))
119 117
120 def genCondCode(self, expr, bbtrue, bbfalse): 118 def genCondCode(self, expr, bbtrue, bbfalse):
121 # Implement sequential logical operators 119 # Implement sequential logical operators
122 assert expr.typ == boolType
123 if type(expr) is astnodes.Binop: 120 if type(expr) is astnodes.Binop:
124 if expr.op == 'or': 121 if expr.op == 'or':
125 l2 = self.newBlock() 122 l2 = self.newBlock()
126 self.genCondCode(expr.a, bbtrue, l2) 123 self.genCondCode(expr.a, bbtrue, l2)
127 self.setBlock(l2) 124 self.setBlock(l2)
178 elif type(expr) is astnodes.TypeCast: 175 elif type(expr) is astnodes.TypeCast:
179 # TODO: improve this mess: 176 # TODO: improve this mess:
180 ar = self.genExprCode(expr.a) 177 ar = self.genExprCode(expr.a)
181 tt = theType(expr.to_type) 178 tt = theType(expr.to_type)
182 if isinstance(tt, astnodes.PointerType): 179 if isinstance(tt, astnodes.PointerType):
183 if expr.a.typ is intType: 180 if expr.a.typ is expr.scope['int']:
184 return ar 181 return ar
185 elif isinstance(expr.a.typ, astnodes.PointerType): 182 elif isinstance(expr.a.typ, astnodes.PointerType):
186 return ar 183 return ar
187 else: 184 else:
188 raise Exception() 185 raise Exception()