Commits

Maciej Fijalkowski  committed 677f50b

start porting virtuals

  • Participants
  • Parent commits 914ee3e
  • Branches result-in-resops

Comments (0)

Files changed (4)

File pypy/jit/metainterp/optimizeopt/virtualize.py

                 self.replace(op, fieldvalue.op)
                 return
         if value.is_virtual():
-            assert isinstance(value, AbstractVirtualValue)
             fieldvalue = value.getfield(op.getdescr(), None)
             if fieldvalue is None:
                 fieldvalue = self.optimizer.new_const(op.getdescr())
-            self.replace(op, fieldvalue.op)
+            self.optimizer.replace(op, fieldvalue)
         else:
             value.ensure_nonnull()
             self.emit_operation(op)
 
         if value.is_virtual():
             fieldvalue = self.getforwarded(op.getarg(1))
-            xxx
             value.setfield(op.getdescr(), fieldvalue)
         else:
             xxx
             return op
 
     def optimize_NEW_WITH_VTABLE(self, op):
-        value = self.getforwarded(op)
-        value.setknownclass(op.getarg(0))
+        pass
 
     def optimize_NEW(self, op):
         self.make_vstruct(op.getdescr(), op)

File pypy/jit/metainterp/optmodel.py

 
 from pypy.tool.sourcetools import func_with_new_name
 from pypy.jit.metainterp.resoperation import opclasses, opclasses_mutable, rop,\
-     INT, REF, ConstInt, Const
+     INT, REF, ConstInt, Const, ConstPtr
 from pypy.jit.metainterp.optimizeopt.intutils import ImmutableIntUnbounded,\
      ConstantIntBound, IntBound
-from pypy.jit.metainterp.virtualmodel import declare_virtual
+from pypy.jit.metainterp.virtualmodel import Virtual
 
 class __extend__(ConstInt):
     def getintbound(self):
     def getboolres(self):
         return False # for optimization
 
+class __extend__(ConstPtr):
+    def is_virtual(self):
+        return False
+
+    def is_forced_virtual(self):
+        return False
+
 class __extend__(Const):
     def getlastguardpos(self):
         return -1
     def is_null(self):
         return not self.nonnull()
 
+opclasses_mutable[rop.NEW_WITH_VTABLE] = Virtual
+
 def create_mutable_subclasses():
     def addattr(cls, attr, default_value=None):
-        cls.attributes_to_copy.append('_' + attr)
+        if hasattr(cls, 'attributes_to_copy'):
+            cls.attributes_to_copy.append('_' + attr)
         def getter(self):
             return getattr(self, '_' + attr)
         def setter(self, value):
     imm_int_unbound = ImmutableIntUnbounded()
     for i, cls in enumerate(opclasses):
         if cls is None:
-            Mutable = None
+            continue
+        elif opclasses_mutable[cls.getopnum()] is not None:
+            addattr(opclasses_mutable[cls.getopnum()], 'lastguardpos')
+            continue
         else:
             class Mutable(cls):
                 is_mutable = True
                     return self
                 def is_virtual(self):
                     return False
-            if op.getopnum() == rop.NEW_WITH_VTABLE:
-                Mutable = declare_virtual(Mutable)
+                def is_forced_virtual(self):
+                    return False
+
             if cls.is_guard() or cls.getopnum() == rop.FINISH:
                 addattr(Mutable, 'failargs')
             if cls.is_guard():
                 addattr(Mutable, 'knownnonnull', False)
                 Mutable.is_nonnull = ref_is_nonnull
                 Mutable.is_null = ref_is_null
-            if cls.getopnum() in (rop.NEW_WITH_VTABLE, rop.NEW):
-                addattr(Mutable, 'isforced', False)
             # for tracking last guard and merging GUARD_VALUE with
             # GUARD_NONNULL etc
             addattr(Mutable, 'lastguardpos', -1)
             Mutable.__name__ = cls.__name__ + '_mutable'
             if Mutable.attributes_to_copy:
                 make_new_copy_function(Mutable, cls)
-        assert len(opclasses_mutable) == i
-        opclasses_mutable.append(Mutable)
-    assert len(opclasses) == len(opclasses_mutable)
+            opclasses_mutable[i] = Mutable
 
 create_mutable_subclasses()

File pypy/jit/metainterp/resoperation.py

     pass
 
 def setup(debug_print=False):
+    global opclasses_mutable
+    
     i = 0
     for basename in _oplist:
         if '/' in basename:
         if k.startswith('CALL'):
             ALLCALLS.append(v)
     opgroups.ALLCALLS = tuple(ALLCALLS)
+    opclasses_mutable = [None] * len(opclasses)
 
 def get_base_class(mixin, tpmixin, base):
     try:

File pypy/jit/metainterp/virtualmodel.py

 
-def declare_virtual(cls):
-    class Virtual(cls):
-        def force(self, optimizer):
-            if not self._isforced:
-                optimizer.emit_operation(self)
-                self._isforced = True
-            return self
-        
-        def is_virtual(self):
-            return not self._isforced
-    return Virtual
+from pypy.jit.metainterp.resoperation import rop, opclasses
+
+NEW_WITH_VTABLE = opclasses[rop.NEW_WITH_VTABLE]
+
+class Virtual(NEW_WITH_VTABLE):
+    is_mutable = True
+
+    def __init__(self, pval):
+        NEW_WITH_VTABLE.__init__(self, pval)
+        self._fields = {} # XXX convert from dict to a list
+        self._is_forced = False
+
+    def getfield(self, ofs, default):
+        return self._fields.get(ofs, default)
+
+    def setfield(self, ofs, fieldvalue):
+        self._fields[ofs] = fieldvalue
+
+    def getknownclass(self):
+        return self.getarg(0)
+
+    def setknownclass(self, cls):
+        pass # ignore
+
+    def is_nonnull(self):
+        return True
+
+    def is_null(self):
+        return False
+
+    def _copy_extra_attrs(self, new):
+        raise Exception("Virtual should not be forwarded")
+    
+    def force(self, optimizer):
+        if not self._is_forced:
+            optimizer.emit_operation(self)
+            self._is_forced = True
+        return self
+
+    def is_virtual(self):
+        return not self._is_forced
+
+    def is_forced_virtual(self):
+        return self._is_forced