[pypy-svn] pypy default: Pick variable to spill based on the longest longevity

bivab commits-noreply at bitbucket.org
Thu Feb 17 14:46:42 CET 2011


Author: David Schneider <david.schneider at picle.org>
Branch: 
Changeset: r42107:519673a58add
Date: 2011-02-17 14:27 +0100
http://bitbucket.org/pypy/pypy/changeset/519673a58add/

Log:	Pick variable to spill based on the longest longevity

diff --git a/pypy/jit/backend/llsupport/regalloc.py b/pypy/jit/backend/llsupport/regalloc.py
--- a/pypy/jit/backend/llsupport/regalloc.py
+++ b/pypy/jit/backend/llsupport/regalloc.py
@@ -160,7 +160,8 @@
                                 need_lower_byte=False):
         """ Silly algorithm.
         """
-        candidates = []
+        cur_max_age = -1
+        candidate = None
         for next in self.reg_bindings:
             reg = self.reg_bindings[next]
             if next in forbidden_vars:
@@ -172,8 +173,13 @@
                     continue
             if need_lower_byte and reg in self.no_lower_byte_regs:
                 continue
-            return next
-        raise NoVariableToSpill
+            max_age = self.longevity[next][1]
+            if cur_max_age < max_age:
+                cur_max_age = max_age
+                candidate = next
+        if candidate is None:
+            raise NoVariableToSpill
+        return candidate
 
     def force_allocate_reg(self, v, forbidden_vars=[], selected_reg=None,
                            need_lower_byte=False):

diff --git a/pypy/jit/backend/llsupport/test/test_regalloc.py b/pypy/jit/backend/llsupport/test/test_regalloc.py
--- a/pypy/jit/backend/llsupport/test/test_regalloc.py
+++ b/pypy/jit/backend/llsupport/test/test_regalloc.py
@@ -16,9 +16,12 @@
     return res, longevity
 
 class FakeReg(object):
-    pass
+    def __init__(self, i):
+        self.n = i
+    def __repr__(self):
+        return 'r%d' % self.n
 
-r0, r1, r2, r3 = [FakeReg() for _ in range(4)]
+r0, r1, r2, r3 = [FakeReg(i) for i in range(4)]
 regs = [r0, r1, r2, r3]
 
 class RegisterManager(BaseRegMan):
@@ -326,3 +329,21 @@
         assert fm.frame_depth == 3
         
         
+
+    def test_spilling(self):
+        b0, b1, b2, b3, b4, b5 = newboxes(0, 1, 2, 3, 4, 5)
+        longevity = {b0: (0, 3), b1: (0, 3), b3: (0, 5), b2: (0, 2), b4: (1, 4), b5: (1, 3)}
+        fm = TFrameManager()
+        asm = MockAsm()
+        rm = RegisterManager(longevity, frame_manager=fm, assembler=asm)
+        rm.next_instruction()
+        for b in b0, b1, b2, b3:
+            rm.force_allocate_reg(b)
+        assert len(rm.free_regs) == 0
+        rm.next_instruction()
+        loc = rm.loc(b3)
+        spilled = rm.force_allocate_reg(b4)
+        assert spilled is loc
+        spilled2 = rm.force_allocate_reg(b5)
+        assert spilled2 is loc
+        rm._check_invariants()


More information about the Pypy-commit mailing list