Mercurial > lcfOS
annotate python/ppci/codegen/codegen.py @ 342:86b02c98a717 devel
Moved target directory
author | Windel Bouwman |
---|---|
date | Sat, 01 Mar 2014 15:40:31 +0100 |
parents | d1ecc493384e |
children | 3bb7dcfe5529 |
rev | line source |
---|---|
336
d1ecc493384e
Added spiffy armtoken class for bit fiddeling. Added cool test that checks for build repeatability
Windel Bouwman
parents:
334
diff
changeset
|
1 from .. import ir |
312 | 2 from ..irutils import Verifier |
342 | 3 from ..target import Target |
210 | 4 from ppci import CompilerError |
296 | 5 from .canon import make as canonicalize |
6 from .registerallocator import RegisterAllocator | |
312 | 7 import logging |
210 | 8 |
290 | 9 |
210 | 10 class CodeGenerator: |
292 | 11 """ Generic code generator """ |
12 def __init__(self, target): | |
290 | 13 # TODO: schedule traces in better order. |
14 # This is optional! | |
292 | 15 assert isinstance(target, Target), target |
312 | 16 self.logger = logging.getLogger('codegen') |
290 | 17 self.target = target |
292 | 18 self.ins_sel = target.ins_sel |
296 | 19 self.ra = RegisterAllocator() |
312 | 20 self.verifier = Verifier() |
290 | 21 |
292 | 22 def generateFunc(self, irfunc, outs): |
290 | 23 """ Generate code for one function into a frame """ |
334 | 24 self.logger.debug('Generating code for {}'.format(irfunc.name)) |
290 | 25 # Create a frame for this function: |
336
d1ecc493384e
Added spiffy armtoken class for bit fiddeling. Added cool test that checks for build repeatability
Windel Bouwman
parents:
334
diff
changeset
|
26 frame = self.target.FrameClass(ir.label_name(irfunc)) |
210 | 27 |
290 | 28 # Canonicalize the intermediate language: |
296 | 29 canonicalize(irfunc, frame) |
334 | 30 self.logger.debug('after canonicalize', extra={'irfunc': irfunc}) |
312 | 31 self.verifier.verify_function(irfunc) |
290 | 32 self.ins_sel.munchFunction(irfunc, frame) |
334 | 33 self.logger.debug('Selected instructions', extra={'ppci_frame': frame}) |
296 | 34 |
290 | 35 # Do register allocation: |
36 self.ra.allocFrame(frame) | |
334 | 37 self.logger.debug('Registers allocated, now adding final glue') |
290 | 38 # TODO: Peep-hole here? |
39 | |
40 # Add label and return and stack adjustment: | |
41 frame.EntryExitGlue3() | |
42 | |
43 # Materialize the register allocated instructions into a stream of | |
44 # real instructions. | |
292 | 45 frame.lower_to(outs) |
334 | 46 self.logger.debug('Instructions materialized') |
290 | 47 return frame |
48 | |
292 | 49 def generate(self, ircode, outs): |
296 | 50 """ Generate code into output stream """ |
336
d1ecc493384e
Added spiffy armtoken class for bit fiddeling. Added cool test that checks for build repeatability
Windel Bouwman
parents:
334
diff
changeset
|
51 assert isinstance(ircode, ir.Module) |
292 | 52 outs.selectSection('code') |
210 | 53 |
290 | 54 # Munch program into a bunch of frames. One frame per function. |
55 # Each frame has a flat list of abstract instructions. | |
56 # Generate code for all functions: | |
296 | 57 self.frames = [self.generateFunc(f, outs) for f in ircode.Functions] |
290 | 58 return self.frames |