changeset 255:7416c923a02a

Added more logging
author Windel Bouwman
date Sun, 04 Aug 2013 15:10:10 +0200
parents bd26dc13f270
children 225f444019b1
files python/c3/analyse.py python/c3/builder.py python/c3/codegenerator.py python/codegenarm.py python/ide.py python/optimize.py python/ppci/errors.py python/stm32.py python/transform.py python/zcc.py
diffstat 10 files changed, 84 insertions(+), 70 deletions(-) [+]
line wrap: on
line diff
--- a/python/c3/analyse.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/c3/analyse.py	Sun Aug 04 15:10:10 2013 +0200
@@ -1,3 +1,4 @@
+import logging
 from .visitor import Visitor
 from .astnodes import *
 from .scope import Scope, topScope
@@ -11,8 +12,10 @@
     """
     def __init__(self, diag):
         self.diag = diag
+        self.logger = logging.getLogger('c3')
 
     def analyzePackage(self, pkg, packageProvider):
+        self.logger.info('Checking package {}'.format(pkg.name))
         self.ok = True
         visitor = Visitor()
         # Prepare top level scope:
--- a/python/c3/builder.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/c3/builder.py	Sun Aug 04 15:10:10 2013 +0200
@@ -36,7 +36,6 @@
         pkg = self.parser.parseSource(src)
         if not pkg:
             return
-        logging.getLogger('c3').info('Source parsed')
 
         # TODO: merge the two below?
         #AstPrinter().printAst(pkg)
--- a/python/c3/codegenerator.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/c3/codegenerator.py	Sun Aug 04 15:10:10 2013 +0200
@@ -1,3 +1,4 @@
+import logging
 import ir
 from . import astnodes
 from .scope import boolType, intType
@@ -8,9 +9,12 @@
     '&':'and', '>>':'shl', '<<':'shr'}
 
 class CodeGenerator:
+    def __init__(self):
+        self.logger = logging.getLogger('c3')
     """ Generates intermediate code from a package """
     def gencode(self, pkg):
         assert type(pkg) is astnodes.Package
+        self.logger.info('Generating ir-code for {}'.format(pkg.name))
         self.varMap = {} # Maps variables to storage locations.
         self.funcMap = {}
         self.builder = ir.Builder()
--- a/python/codegenarm.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/codegenarm.py	Sun Aug 04 15:10:10 2013 +0200
@@ -1,3 +1,4 @@
+import logging
 import ir
 from target import Label, Comment, Alignment, LabelRef, Imm32, DebugInfo
 import cortexm3 as arm
@@ -10,12 +11,14 @@
     """
     def __init__(self, out):
         self.outs = out
+        self.logger = logging.getLogger('cgarm')
 
     def emit(self, item):
         self.outs.emit(item)
 
     def generate(self, ircode):
         assert isinstance(ircode, ir.Module)
+        self.logger.info('Generating arm code for {}'.format(ircode.name))
         # TODO: get these from linker descriptor?
         self.outs.getSection('code').address = 0x08000000
         self.outs.getSection('data').address = 0x20000000
--- a/python/ide.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/ide.py	Sun Aug 04 15:10:10 2013 +0200
@@ -2,6 +2,7 @@
 
 import sys
 import os
+import logging
 
 from PyQt4.QtCore import *
 from PyQt4.QtGui import *
@@ -14,16 +15,21 @@
 import c3
 import zcc
 import outstream
-import logging
 
 
 class BuildOutput(QTextEdit):
     """ Build output component """
     def __init__(self, parent=None):
-      super(BuildOutput, self).__init__(parent)
-      self.setCurrentFont(QFont('Courier'))
-      self.setReadOnly(True)
-      self.append('Build output will appear here!')
+        super(BuildOutput, self).__init__(parent)
+        fmt = logging.Formatter(fmt='%(asctime)s %(levelname)s %(name)s %(msg)s')
+        class MyHandler(logging.Handler):
+            def emit(self2, x):
+                self.append(str(fmt.format(x)))
+
+        logging.getLogger().addHandler(MyHandler())
+        self.setCurrentFont(QFont('Courier'))
+        self.setReadOnly(True)
+        logging.info('Build output will appear here!')
 
 
 class BuildErrors(QTreeView):
@@ -81,6 +87,8 @@
 class Ide(QMainWindow):
     def __init__(self, parent=None):
         super(Ide, self).__init__(parent)
+
+
         self.setWindowTitle('LCFOS IDE')
         icon = QIcon('icons/logo.png')
         self.setWindowIcon(icon)
@@ -108,9 +116,9 @@
 
         self.buildOutput = addComponent('Build output', BuildOutput())
         self.astViewer = addComponent('AST viewer', AstViewer())
-        self.astViewer.sigNodeSelected.connect(self.nodeSelected)
+        self.astViewer.sigNodeSelected.connect(lambda node: self.showLoc(node.loc))
         self.builderrors = addComponent('Build errors', BuildErrors())
-        self.builderrors.sigErrorSelected.connect(self.errorSelected)
+        self.builderrors.sigErrorSelected.connect(lambda err: self.showLoc(err.loc))
         self.devxplr = addComponent('Device explorer', stutil.DeviceExplorer())
         self.regview = addComponent('Registers', stutil.RegisterView())
         self.memview = addComponent('Memory', stutil.MemoryView())
@@ -224,9 +232,6 @@
     def nodeSelected(self, node):
         self.showLoc(node.loc)
 
-    def errorSelected(self, err):
-        self.showLoc(err.loc)
-
     def showLoc(self, loc):
         ce = self.activeMdiChild()
         if not ce:
@@ -257,48 +262,42 @@
         if not ce:
             return
         self.diag.clear()
-        self.buildOutput.append('Starting parse')
         pkg = self.c3front.parse(ce.Source)
 
         # Set errors:
-        for err in self.diag.diags:
-            self.buildOutput.append(str(err))
         self.builderrors.setErrorList(self.diag.diags)
         ce.setErrors(self.diag.diags)
         self.astViewer.setAst(pkg)
-        self.buildOutput.append("Done!")
+        logging.info('Done!')
 
     def buildFile(self):
         ce = self.activeMdiChild()
         if not ce:
             return
         self.diag.clear()
-        self.buildOutput.append('Starting build')
         outs = outstream.TextOutputStream()
         if not zcc.zcc(ce.Source, outs, self.diag):
             # Set errors:
-            for err in self.diag.diags:
-                self.buildOutput.append(str(err))
             self.builderrors.setErrorList(self.diag.diags)
             ce.setErrors(self.diag.diags)
             return
 
         code_s = outs.getSection('code')
         self.debugInfo = code_s.debugInfos()
-        self.buildOutput.append("Flashing stm32f4 discovery")
         if self.ctrlToolbar.device:
+            logging.info('Flashing stm32f4 discovery')
             bts = code_s.to_bytes()
             self.ctrlToolbar.device.writeFlash(0x08000000, bts)
             stl = self.ctrlToolbar.device.iface
             stl.reset()
             stl.halt()
-
-        self.buildOutput.append("Done!")
+        logging.info('Done!')
 
 if __name__ == '__main__':
-    logging.basicConfig(level=logging.DEBUG)
+    logging.basicConfig(format='%(asctime)s %(levelname)s %(name)s %(message)s', level=logging.DEBUG)
     app = QApplication(sys.argv)
     ide = Ide()
     ide.show()
+    logging.info('IDE started')
     app.exec_()
 
--- a/python/optimize.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/optimize.py	Sun Aug 04 15:10:10 2013 +0200
@@ -8,16 +8,13 @@
     m2r = Mem2RegPromotor()
     clr = CleanPass()
     cse = CommonSubexpressionElimination()
-    ir.check()
     cf.run(ir)
     dcd.run(ir)
-    ir.check()
     clr.run(ir)
-    ir.check()
     m2r.run(ir)
-    ir.check()
     cse.run(ir)
-    ir.check()
+    cf.run(ir)
+    dcd.run(ir)
 
 
 
--- a/python/ppci/errors.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/ppci/errors.py	Sun Aug 04 15:10:10 2013 +0200
@@ -3,6 +3,7 @@
    Diagnostic utils
 """
 
+import logging
 from . import SourceLocation
 
 class CompilerError(Exception):
@@ -50,8 +51,10 @@
 class DiagnosticsManager:
     def __init__(self):
         self.diags = []
+        self.logger = logging.getLogger('diagnostics')
 
     def addDiag(self, d):
+        self.logger.info(str(d))
         self.diags.append(d)
 
     def error(self, msg, loc):
--- a/python/stm32.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/stm32.py	Sun Aug 04 15:10:10 2013 +0200
@@ -27,6 +27,7 @@
    """
    def __init__(self, iface):
       super().__init__(iface)
+      self.logger = logging.getLogger('stm32')
 
    def __str__(self):
       return 'STM32F4 device size=0x{1:X} id=0x{0:X}'.format(\
@@ -85,21 +86,21 @@
       if address & 1 == 1:
          raise STLinkException('Unaligned flash')
       if len(content) & 1 == 1:
-         print('unaligned length, padding with zero')
+         self.logger.warning('unaligned length, padding with zero')
          content += bytes([0])
       if address & (pagesize - 1) != 0:
          raise STLinkException('Address not aligned with pagesize')
       # erase required space
       sectors = self.calcSectors(address, len(content))
-      print('erasing {0} sectors'.format(len(sectors)))
+      self.logger.info('erasing {0} sectors'.format(len(sectors)))
       for sector, secsize in sectors:
-         print('erasing sector {0} of {1} bytes'.format(sector, secsize))
+         self.logger.info('erasing sector {0} of {1} bytes'.format(sector, secsize))
          self.eraseFlashSector(sector)
       # program pages:
       self.unlockFlashIf()
       self.writeFlashCrPsiz(2) # writes are 32 bits aligned
       self.setFlashCrPg()
-      print('writing {0} bytes'.format(len(content)), end='')
+      self.logger.info('writing {0} bytes'.format(len(content)), end='')
       offset = 0
       t1 = time.time()
       while offset < len(content):
--- a/python/transform.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/transform.py	Sun Aug 04 15:10:10 2013 +0200
@@ -7,12 +7,17 @@
 # Standard passes:
 
 class FunctionPass:
+    def __init__(self):
+        self.logger = logging.getLogger('optimize')
+
     def run(self, ir):
         """ Main entry point for the pass """
-        logging.info('Running pass {}'.format(type(self)))
+        self.logger.info('Running pass {}'.format(type(self)))
+        ir.check()
         self.prepare()
         for f in ir.Functions:
             self.onFunction(f)
+        ir.check()
 
     def onFunction(self, f):
         """ Override this virtual method """
@@ -42,34 +47,33 @@
         raise NotImplementedError()
 
 # Usefull transforms:
-class ConstantFolder(InstructionPass):
-    def prepare(self):
-        self.constMap = {}
-
-    def onInstruction(self, i):
-      if type(i) is ImmLoad:
-         self.constMap[i.target] = i.value
-      elif type(i) is BinaryOperator:
-         if i.value1 in self.constMap and i.value2 in self.constMap and i.operation in ['+', '-', '*', '<<']:
-            op = i.operation
-            va = self.constMap[i.value1]
-            vb = self.constMap[i.value2]
-            if op == '+':
-               vr = va + vb
-            elif op == '*':
-               vr = va * vb
-            elif op == '-':
-               vr = va - vb
-            elif op == '<<':
-                vr = va << vb
-            else:
-               vr = None
-               return
-            self.constMap[i.result] = vr
-            i.removeDef(i.result)
-            i2 = ImmLoad(i.result, vr)
-            logging.debug('Replacing {}'.format(i))
-            i.Parent.replaceInstruction(i, i2)
+class ConstantFolder(BasicBlockPass):
+    def onBasicBlock(self, bb):
+        constMap = {}
+        ins = [i for i in bb.Instructions if type(i) in [ImmLoad, BinaryOperator]]
+        for i in ins:
+            if type(i) is ImmLoad:
+                constMap[i.target] = i.value
+            elif type(i) is BinaryOperator:
+                if i.value1 in constMap and i.value2 in constMap and i.operation in ['+', '-', '*', '<<']:
+                    op = i.operation
+                    va = constMap[i.value1]
+                    vb = constMap[i.value2]
+                    if op == '+':
+                       vr = va + vb
+                    elif op == '*':
+                       vr = va * vb
+                    elif op == '-':
+                       vr = va - vb
+                    elif op == '<<':
+                        vr = va << vb
+                    else:
+                        raise NotImplementedError()
+                    constMap[i.result] = vr
+                    i.removeDef(i.result)
+                    i2 = ImmLoad(i.result, vr)
+                    logging.debug('Replacing {} with {}'.format(i, i2))
+                    i.Parent.replaceInstruction(i, i2)
 
 
 class DeadCodeDeleter(BasicBlockPass):
--- a/python/zcc.py	Wed Jul 31 21:20:58 2013 +0200
+++ b/python/zcc.py	Sun Aug 04 15:10:10 2013 +0200
@@ -19,21 +19,23 @@
 parser.add_argument('source', type=argparse.FileType('r'), \
   help='the source file to build')
 parser.add_argument('--dumpir', action='store_true', help="Dump IR-code")
+parser.add_argument('--dumpasm', action='store_true', help="Dump ASM-code")
+parser.add_argument('--optimize', action='store_true', help="Optimize")
 parser.add_argument('-o', '--output', help='Output file', metavar='filename')
 parser.add_argument('--hexfile', help='Output hexfile', type=argparse.FileType('w'))
 parser.add_argument('--log', help='Log level (INFO,DEBUG)', type=logLevel)
 
-def zcc(src, outs, diag, dumpir=False):
+def zcc(src, outs, diag, dumpir=False, do_optimize=False):
+    logging.info('Zcc started')
     # Front end:
     c3b = c3.Builder(diag)
     ircode = c3b.build(src)
-    logging.info('Intermediate code generated')
     if not ircode:
         return
 
     # Optimization passes:
-    optimize(ircode)
-    logging.info('IR-code optimized')
+    if do_optimize:
+        optimize(ircode)
 
     if dumpir:
         ircode.dump()
@@ -44,21 +46,20 @@
     return True
 
 def main(args):
-    logging.basicConfig(format='%(asctime)s %(levelname)s %(message)s', level=args.log)
+    logging.basicConfig(format='%(asctime)s %(levelname)s %(name)s %(message)s', level=args.log)
     src = args.source.read()
     args.source.close()
-    logging.info('Source loaded')
     diag = ppci.DiagnosticsManager()
     outs = outstream.TextOutputStream()
 
     # Invoke compiler:
-    res = zcc(src, outs, diag, dumpir=args.dumpir)
+    res = zcc(src, outs, diag, dumpir=args.dumpir, do_optimize=args.optimize)
     if not res:
         diag.printErrors(src)
         sys.exit(1)
 
-    #if args.dumpir:
-    #    outs.dump()
+    if args.dumpasm:
+        outs.dump()
 
     code_bytes = outs.sections['code'].to_bytes()
     #print('bytes:', code_bytes)
@@ -71,10 +72,10 @@
         f.write(code_bytes)
 
     if args.hexfile:
+        logging.info('Creating hexfile')
         hf = hexfile.HexFile()
         hf.addRegion(0x08000000, code_bytes)
         hf.save(args.hexfile)
-        logging.info('Hexfile created')
 
 if __name__ == '__main__':
     arguments = parser.parse_args()