# HG changeset patch # User Windel Bouwman # Date 1366452051 -7200 # Node ID 5fd02aa38b42d9a0d1fe456469186dde754197d3 # Parent a51b3c95638602b8c636accb7e7e139cda6b5eac Added while loop code generation diff -r a51b3c956386 -r 5fd02aa38b42 python/c3/astnodes.py --- a/python/c3/astnodes.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/c3/astnodes.py Sat Apr 20 12:00:51 2013 +0200 @@ -156,9 +156,9 @@ return 'IF-statement' class WhileStatement(Node): - def __init__(self, condition, statements): + def __init__(self, condition, statement): self.condition = condition - self.dostatements = statements + self.dostatement = statement def __repr__(self): return 'WHILE-statement' diff -r a51b3c956386 -r 5fd02aa38b42 python/c3/codegenerator.py --- a/python/c3/codegenerator.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/c3/codegenerator.py Sat Apr 20 12:00:51 2013 +0200 @@ -69,6 +69,7 @@ self.builder.addIns(ir.Branch(te)) self.builder.setBB(te) elif type(code) is astnodes.FunctionCall: + print('TODO') pass elif type(code) is astnodes.EmptyStatement: pass @@ -78,6 +79,17 @@ self.builder.addIns(ir.Return(re)) else: self.builder.addIns(ir.Return()) + elif type(code) is astnodes.WhileStatement: + bbdo = self.builder.newBB() + bbtest = self.builder.newBB() + te = self.builder.newBB() + self.builder.addIns(ir.Branch(bbtest)) + self.builder.setBB(bbtest) + self.genCondCode(code.condition, bbdo, te) + self.builder.setBB(bbdo) + self.genCode(code.dostatement) + self.builder.addIns(ir.Branch(bbtest)) + self.builder.setBB(te) else: print('Unknown stmt:', code) def genCondCode(self, expr, bbtrue, bbfalse): diff -r a51b3c956386 -r 5fd02aa38b42 python/c3/visitor.py --- a/python/c3/visitor.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/c3/visitor.py Sat Apr 20 12:00:51 2013 +0200 @@ -40,6 +40,9 @@ elif type(node) in [EmptyStatement, VariableUse, Variable, Literal, FunctionType]: # Those nodes do not have child nodes. pass + elif type(node) is WhileStatement: + self.visit(node.condition) + self.visit(node.dostatement) else: print('UNK visit "{0}"'.format(node)) self.f2(node) diff -r a51b3c956386 -r 5fd02aa38b42 python/ir/instruction.py --- a/python/ir/instruction.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/ir/instruction.py Sat Apr 20 12:00:51 2013 +0200 @@ -6,15 +6,9 @@ def __init__(self, name): # TODO: add typing? for now only handle integers self.name = name - self.interferes = set() - self.reg = None self.used_by = [] def __repr__(self): - if self.reg: - n = self.reg - else: - n = self.name - return '{0}'.format(n) # + str(self.IsUsed) + return '{0}'.format(self.name) # + str(self.IsUsed) @property def IsUsed(self): return len(self.used_by) > 0 diff -r a51b3c956386 -r 5fd02aa38b42 python/testir.py --- a/python/testir.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/testir.py Sat Apr 20 12:00:51 2013 +0200 @@ -36,7 +36,11 @@ if (x > 13) { - res = res + 2; + while (y > 1337) + { + res = res + 2; + y = y - 12; + } } return res; } @@ -58,6 +62,12 @@ dcd.run(ir) m2r.run(ir) #ir.dump() + + # Dump a graphiz file: + with open('graaf.gv', 'w') as f: + ir.dumpgv(f) + os.system('dot -Tpdf -ograaf.pdf graaf.gv') + asm = cgenx86.genBin(ir) #for a in asm: # print(a) @@ -65,9 +75,3 @@ f.write('BITS 64\n') for a in asm: f.write(str(a) + '\n') - - # Dump a graphiz file: - with open('graaf.gv', 'w') as f: - ir.dumpgv(f) - os.system('dot -Tpdf -ograaf.pdf graaf.gv') - diff -r a51b3c956386 -r 5fd02aa38b42 python/transform.py --- a/python/transform.py Fri Apr 19 22:15:54 2013 +0200 +++ b/python/transform.py Sat Apr 20 12:00:51 2013 +0200 @@ -4,11 +4,14 @@ class FunctionPass: def run(self, ir): """ Main entry point for the pass """ + self.prepare() for f in ir.Functions: self.onFunction(f) def onFunction(self, f): """ Override this virtual method """ raise NotImplementedError() + def prepare(self): + pass class BasicBlockPass(FunctionPass): def onFunction(self, f): @@ -28,23 +31,28 @@ # Usefull transforms: class ConstantFolder(InstructionPass): + def prepare(self): + self.constMap = {} def onInstruction(self, i): if type(i) is ImmLoad: - i.target.constval = i.value + self.constMap[i.target] = i.value elif type(i) is BinaryOperator: - a = i.value1 - b = i.value2 - if hasattr(a, 'constval') and hasattr(b,'constval'): + if i.value1 in self.constMap and i.value2 in self.constMap: op = i.operation + va = self.constMap[i.value1] + vb = self.constMap[i.value2] if op == '+': - i2 = ImmLoad(i.result, a.constval + b.constval) - i.Parent.replaceInstruction(i, i2) + vr = va + vb elif op == '*': - i2 = ImmLoad(i.result, a.constval * b.constval) - i.Parent.replaceInstruction(i, i2) + vr = va * vb elif op == '-': - i2 = ImmLoad(i.result, a.constval - b.constval) - i.Parent.replaceInstruction(i, i2) + vr = va - vb + else: + vr = None + return + self.constMap[i.result] = vr + i2 = ImmLoad(i.result, vr) + i.Parent.replaceInstruction(i, i2) class DeadCodeDeleter(BasicBlockPass): def onBasicBlock(self, bb): @@ -71,5 +79,6 @@ class Mem2RegPromotor(FunctionPass): def onFunction(self, f): + # TODO print(f)