[pypy-svn] r77350 - in pypy/branch/jit-loop-invaraints/pypy/jit/metainterp: optimizeopt test

hakanardo at codespeak.net hakanardo at codespeak.net
Fri Sep 24 17:16:01 CEST 2010


Author: hakanardo
Date: Fri Sep 24 17:15:59 2010
New Revision: 77350

Modified:
   pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/__init__.py
   pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/invariant.py
   pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/optimizer.py
   pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/virtualize.py
   pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/test/test_basic.py
Log:
Inlines the preamble, but still tries to call the preamble. Why?

Modified: pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/__init__.py
==============================================================================
--- pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/__init__.py	(original)
+++ pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/__init__.py	Fri Sep 24 17:15:59 2010
@@ -11,15 +11,18 @@
     must be applicable to the loop; you will probably get an AssertionError
     if not.
     """
-    optimizations = [OptIntBounds(),
+    optimizations = [OptInvariant(),
+                     OptIntBounds(),
                      OptRewrite(),
                      OptVirtualize(),
                      OptHeap(),
-                     OptInvariant(),
                      ]
 
     optimizer = Optimizer(metainterp_sd, loop, optimizations, virtuals)
     optimizer.propagate_all_forward()
+    print
+    print
+    print loop.operations
 
 def optimize_bridge_1(metainterp_sd, bridge):
     """The same, but for a bridge.  The only difference is that we don't

Modified: pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/invariant.py
==============================================================================
--- pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/invariant.py	(original)
+++ pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/invariant.py	Fri Sep 24 17:15:59 2010
@@ -1,5 +1,6 @@
 from pypy.jit.metainterp.optimizeopt.optimizer import *
 from pypy.jit.metainterp.resoperation import rop, ResOperation
+from pypy.jit.metainterp.compile import prebuiltNotSpecNode
 
 class OptInvariant(Optimization):
     """Move loop invariant code into a preamble.
@@ -8,45 +9,81 @@
         if not virtuals:
             return
         
-        inputargs = self.optimizer.original_inputargs
+        #inputargs = self.optimizer.original_inputargs
+        inputargs = self.optimizer.loop.inputargs
         if not inputargs:
             return
         
         jump_op = self.optimizer.loop.operations[-1]
-        assert(jump_op.opnum == rop.JUMP)
-        #for arg_in, arg_out in zip(inputargs, jump_op.args):
-        print
-        print inputargs, jump_op.args
+        if jump_op.opnum != rop.JUMP:
+            return 
+
         for i in range(len(inputargs)):
             arg_in, arg_out = inputargs[i], jump_op.args[i]
             if arg_in is arg_out:
-                print "Invariant: ", arg_in
                 v = self.getvalue(arg_in)
                 v.invariant = True
-        self.invariant_boxes = []
-        
+
+    def invariant_boxes(self):
+        invariant_boxes = []
+        for op in self.optimizer.preamble:
+            if self.get_constant_box(op.result) is None:
+                v = self.getvalue(op.result)
+                v.invariant = True
+                box = v.force_box() 
+                if box and box not in invariant_boxes:
+                    invariant_boxes.append(box)
+        return invariant_boxes
+
     def propagate_forward(self, op):
     
         if op.opnum == rop.JUMP:
             loop = self.optimizer.loop
             if loop.preamble and len(self.optimizer.preamble)>0:
+                # First trace through loop, create preamble
+                self.emit_operation(op)
                 preamble = loop.preamble
                 preamble.inputargs = loop.inputargs[:]
-                loop.inputargs.extend(self.invariant_boxes)
-                op.args = op.args + self.invariant_boxes
+
+                invariant_boxes = self.invariant_boxes()
+                loop.inputargs.extend(invariant_boxes)
+                op.args = op.args + invariant_boxes
                 preamble.operations = self.optimizer.preamble
-                preamble.token.specnodes = loop.token.specnodes
+                preamble.token.specnodes = loop.token.specnodes 
+                loop.token.specnodes = loop.token.specnodes + \
+                                       [prebuiltNotSpecNode] * len(invariant_boxes)
+
+                print
+                print loop.token.number
+                print len(loop.token.specnodes)
                 jmp = ResOperation(rop.JUMP,
                                    loop.inputargs[:],
                                    None)
                 jmp.descr = loop.token
                 preamble.operations.append(jmp)
+                preamble.token.preamble = preamble
+                return
+
+            elif op.descr.preamble:
+                # Bridge calling a loop with preamble, inline it
+                #
+                print
+                print "hi: ", op
+                print loop
+                print
+                self.inline(op.descr.preamble, op.args)
+                return
 
         elif (op.is_always_pure()):# or op.is_foldable_guard() or op.is_ovf()):
             if self.has_invariant_args(op):
-                self.emit_invariant(op)
+                op.invariant = True
+                self.emit_operation(op)
+                if self.get_constant_box(op.result) is None:
+                    v = self.getvalue(op.result)
+                    v.invariant = True
                 return
 
+
         #elif op.is_guard_overflow():
         #    prev_op = self.optimizer.loop.operations[self.optimizer.i - 1]
         #    v = self.getvalue(prev_op.result)
@@ -56,17 +93,6 @@
             
         self.emit_operation(op)
 
-    def emit_invariant(self, op):
-        print "P: ", op, op.opnum
-        op.invariant = True
-        self.emit_operation(op)
-        if self.get_constant_box(op.result) is None:
-            v = self.getvalue(op.result)
-            v.invariant = True
-            box = v.force_box() 
-            if box and box not in self.invariant_boxes:
-                self.invariant_boxes.append(box)
-            
     def has_invariant_args(self, op):
         for a in op.args:
             if self.get_constant_box(a) is None:
@@ -76,4 +102,17 @@
                 if not v.invariant:
                     return False
         return True
+
+    def inline(self, loop, inputargs):
+        argmap = {}
+        for i in range(len(inputargs)):
+           argmap[loop.inputargs[i]] = inputargs[i]
+        for op in loop.operations:
+            newop = op.clone()
+            newop.args = [argmap[a] for a in op.args]
+            if op.result:
+                newop.result = op.result.clonebox()
+                argmap[op.result] = newop.result
+            self.emit_operation(newop)
+        
         

Modified: pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/optimizer.py
==============================================================================
--- pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/optimizer.py	(original)
+++ pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/optimizer.py	Fri Sep 24 17:15:59 2010
@@ -203,7 +203,7 @@
         self.pendingfields = []
         self.preamble = []
 
-        self.original_inputargs = self.loop.inputargs
+        #self.original_inputargs = self.loop.inputargs
 
         if optimizations:
             self.first_optimization = optimizations[0]

Modified: pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/virtualize.py
==============================================================================
--- pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/virtualize.py	(original)
+++ pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/optimizeopt/virtualize.py	Fri Sep 24 17:15:59 2010
@@ -284,6 +284,9 @@
 
     def optimize_JUMP(self, op):
         orgop = self.optimizer.loop.operations[-1]
+        #orgop.descr = op.descr
+        orgop = op
+        print 'Nbr: ', op.descr.number
         exitargs = []
         target_loop_token = orgop.descr
         assert isinstance(target_loop_token, LoopToken)

Modified: pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/test/test_basic.py
==============================================================================
--- pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/test/test_basic.py	(original)
+++ pypy/branch/jit-loop-invaraints/pypy/jit/metainterp/test/test_basic.py	Fri Sep 24 17:15:59 2010
@@ -303,7 +303,7 @@
                     found += 1
             assert found == 1
 
-    def test_loop_invariant_mul(self):
+    def test_loop_invariant_mul1(self):
         myjitdriver = JitDriver(greens = [], reds = ['y', 'res', 'x'])
         def f(x, y):
             res = 0
@@ -340,6 +340,22 @@
                           'int_mul': 1,
                           'jump': 2})
 
+    def test_loop_invariant_mul_guard(self):
+        myjitdriver = JitDriver(greens = [], reds = ['y', 'res', 'x'])
+        def f(x, y):
+            res = 0
+            while y > 0:
+                myjitdriver.can_enter_jit(x=x, y=y, res=res)
+                myjitdriver.jit_merge_point(x=x, y=y, res=res)
+                res += x * x
+                if y<8:
+                    x += 1
+                y -= 1
+            return res
+        res = self.meta_interp(f, [6, 16])
+        assert res == 265
+        self.check_loop_count(3)
+
     def test_loop_invariant_intbox(self):
         myjitdriver = JitDriver(greens = [], reds = ['y', 'res', 'x'])
         class I:



More information about the Pypy-commit mailing list