[Python-checkins] CVS: /python/nondist/src/Compiler compile.py,1.13,1.14

Jeremy Hylton jhylton@cnri.reston.va.us
Tue, 15 Feb 2000 18:45:29 -0500


Update of /projects/cvsroot//python/nondist/src/Compiler
In directory goon.cnri.reston.va.us:/home/jhylton/python/nondist/src/Compiler

Modified Files:
	compile.py 
Log Message:
finish first impl of code generator

add support for nodes TryExcept, TryFinally, Sliceobj
fix visitSubscript to properly handle x[a,b,c]





Index: compile.py
===================================================================
RCS file: /projects/cvsroot//python/nondist/src/Compiler/compile.py,v
retrieving revision 1.13
retrieving revision 1.14
diff -C2 -r1.13 -r1.14
*** compile.py	2000/02/14 23:57:56	1.13
--- compile.py	2000/02/15 23:45:26	1.14
***************
*** 156,167 ****
  
  class CodeGenerator:
!     """TODO
  
-     EmptyNode
-     Sliceobj
-     Tryexcept
-     Tryfinally
-     """
- 
      OPTIMIZED = 1
  
--- 156,161 ----
  
  class CodeGenerator:
!     """Generate bytecode for the Python VM"""
  
      OPTIMIZED = 1
  
***************
*** 426,429 ****
--- 420,480 ----
          self.emit('JUMP_ABSOLUTE', l.startAnchor)
  
+     def visitTryExcept(self, node):
+         # XXX need to figure out exactly what is on the stack when an
+         # exception is raised and the first handler is checked
+         handlers = StackRef()
+         end = StackRef()
+         if node.else_:
+             lElse = StackRef()
+         else:
+             lElse = end
+         self.emit('SET_LINENO', node.lineno)
+         self.emit('SETUP_EXCEPT', handlers)
+         self.visit(node.body)
+         self.emit('POP_BLOCK')
+         self.emit('JUMP_FORWARD', lElse)
+         handlers.bind(self.code.getCurInst())
+         
+         last = len(node.handlers) - 1
+         for i in range(len(node.handlers)):
+             expr, target, body = node.handlers[i]
+             if hasattr(expr, 'lineno'):
+                 self.emit('SET_LINENO', expr.lineno)
+             if expr:
+                 self.emit('DUP_TOP')
+                 self.visit(expr)
+                 self.emit('COMPARE_OP', "exception match")
+                 next = StackRef()
+                 self.emit('JUMP_IF_FALSE', next)
+                 self.emit('POP_TOP')
+             self.emit('POP_TOP')
+             if target:
+                 self.visit(target)
+             else:
+                 self.emit('POP_TOP')
+             self.emit('POP_TOP')
+             self.visit(body)
+             self.emit('JUMP_FORWARD', end)
+             next.bind(self.code.getCurInst())
+             self.emit('POP_TOP')
+         self.emit('END_FINALLY')
+         if node.else_:
+             lElse.bind(self.code.getCurInst())
+             self.visit(node.else_)
+         end.bind(self.code.getCurInst())
+         return 1
+     
+     def visitTryFinally(self, node):
+         final = StackRef()
+         self.emit('SET_LINENO', node.lineno)
+         self.emit('SETUP_FINALLY', final)
+         self.visit(node.body)
+         self.emit('POP_BLOCK')
+         self.emit('LOAD_CONST', None)
+         final.bind(self.code.getCurInst())
+         self.visit(node.final)
+         self.emit('END_FINALLY')
+         return 1
+ 
      def visitCompare(self, node):
  	"""Comment from compile.c follows:
***************
*** 493,500 ****
      def visitSubscript(self, node):
          self.visit(node.expr)
!         for sub in node.subs[:-1]:
              self.visit(sub)
!             self.emit('BINARY_SUBSCR')
!         self.visit(node.subs[-1])
          if node.flags == 'OP_APPLY':
              self.emit('BINARY_SUBSCR')
--- 544,551 ----
      def visitSubscript(self, node):
          self.visit(node.expr)
!         for sub in node.subs:
              self.visit(sub)
!         if len(node.subs) > 1:
!             self.emit('BUILD_TUPLE', len(node.subs))
          if node.flags == 'OP_APPLY':
              self.emit('BINARY_SUBSCR')
***************
*** 503,507 ****
  	elif node.flags == 'OP_DELETE':
              self.emit('DELETE_SUBSCR')
!             
          return 1
  
--- 554,558 ----
  	elif node.flags == 'OP_DELETE':
              self.emit('DELETE_SUBSCR')
!         print
          return 1
  
***************
*** 522,527 ****
              self.emit('DELETE_SLICE+%d' % slice)
          else:
!             print node.flags
              raise
          return 1
  
--- 573,585 ----
              self.emit('DELETE_SLICE+%d' % slice)
          else:
!             print "weird slice", node.flags
              raise
+         return 1
+ 
+     def visitSliceobj(self, node):
+         for child in node.nodes:
+             print child
+             self.visit(child)
+         self.emit('BUILD_SLICE', len(node.nodes))
          return 1