[pypy-svn] r5063 - in pypy/trunk/src/pypy: interpreter objspace objspace/std objspace/std/test

arigo at codespeak.net arigo at codespeak.net
Fri Jun 11 20:01:18 CEST 2004


Author: arigo
Date: Fri Jun 11 20:01:13 2004
New Revision: 5063

Modified:
   pypy/trunk/src/pypy/interpreter/typedef.py
   pypy/trunk/src/pypy/objspace/std/booltype.py
   pypy/trunk/src/pypy/objspace/std/dicttype.py
   pypy/trunk/src/pypy/objspace/std/floattype.py
   pypy/trunk/src/pypy/objspace/std/inttype.py
   pypy/trunk/src/pypy/objspace/std/itertype.py
   pypy/trunk/src/pypy/objspace/std/listtype.py
   pypy/trunk/src/pypy/objspace/std/longtype.py
   pypy/trunk/src/pypy/objspace/std/nonetype.py
   pypy/trunk/src/pypy/objspace/std/objecttype.py
   pypy/trunk/src/pypy/objspace/std/objspace.py
   pypy/trunk/src/pypy/objspace/std/slicetype.py
   pypy/trunk/src/pypy/objspace/std/stdtypedef.py
   pypy/trunk/src/pypy/objspace/std/stringtype.py
   pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py
   pypy/trunk/src/pypy/objspace/std/tupletype.py
   pypy/trunk/src/pypy/objspace/std/typeobject.py
   pypy/trunk/src/pypy/objspace/std/typetype.py
   pypy/trunk/src/pypy/objspace/trivial.py
Log:
- enforced single inheritance at the TypeDef level.
- cleaned up StdTypeDef by merging the 'base' stuff to TypeDef.
- changed all objspace/std/xxxtype.py to use single inheritance
  and default to the object_typedef base.
- fixed the trivial object space accordingly.
- new test for 'class A(int, dict)' failing.


Modified: pypy/trunk/src/pypy/interpreter/typedef.py
==============================================================================
--- pypy/trunk/src/pypy/interpreter/typedef.py	(original)
+++ pypy/trunk/src/pypy/interpreter/typedef.py	Fri Jun 11 20:01:13 2004
@@ -7,15 +7,11 @@
 from pypy.interpreter.error import OperationError
 
 class TypeDef:
-    def __init__(self, __name, **rawdict):
+    def __init__(self, __name, __base=None, **rawdict):
         self.name = __name
+        self.base = __base
         self.rawdict = rawdict
 
-    def mro(self, space):
-        if self is space.object_typedef:
-            return [self]
-        else:
-            return [self, space.object_typedef]
 
 class GetSetProperty(Wrappable):
     def __init__(self, fget, fset=None, fdel=None, doc=None):
@@ -78,7 +74,7 @@
 
 from pypy.interpreter.eval import Code, Frame
 from pypy.interpreter.pycode import PyCode
-from pypy.interpreter.pyframe import PyFrame
+from pypy.interpreter.pyframe import PyFrame, ControlFlowException
 from pypy.interpreter.module import Module
 from pypy.interpreter.function import Function, Method, StaticMethod
 from pypy.interpreter.pytraceback import PyTraceback
@@ -171,3 +167,5 @@
 )
 
 Cell.typedef = TypeDef("Cell")
+
+ControlFlowException.typedef = TypeDef("ControlFlowException")

Modified: pypy/trunk/src/pypy/objspace/std/booltype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/booltype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/booltype.py	Fri Jun 11 20:01:13 2004
@@ -10,6 +10,6 @@
 
 # ____________________________________________________________
 
-bool_typedef = StdTypeDef("bool", [int_typedef],
+bool_typedef = StdTypeDef("bool", int_typedef,
     __new__ = newmethod(descr__new__),
     )

Modified: pypy/trunk/src/pypy/objspace/std/dicttype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/dicttype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/dicttype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 from pypy.objspace.std.register_all import register_all
 
 dict_copy       = MultiMethod('copy',          1)
@@ -101,7 +100,7 @@
 
 # ____________________________________________________________
 
-dict_typedef = StdTypeDef("dict", [object_typedef],
+dict_typedef = StdTypeDef("dict",
     __new__ = newmethod(descr__new__),
     )
 dict_typedef.registermethods(globals())

Modified: pypy/trunk/src/pypy/objspace/std/floattype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/floattype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/floattype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 def descr__new__(space, w_floattype, w_value=None):
     if w_value is None:
@@ -17,6 +16,6 @@
 
 # ____________________________________________________________
 
-float_typedef = StdTypeDef("float", [object_typedef],
+float_typedef = StdTypeDef("float",
     __new__ = newmethod(descr__new__),
     )

Modified: pypy/trunk/src/pypy/objspace/std/inttype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/inttype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/inttype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 from pypy.interpreter.error import OperationError
 
 def descr__new__(space, w_inttype, w_value=None, w_base=None):
@@ -33,6 +32,6 @@
 
 # ____________________________________________________________
 
-int_typedef = StdTypeDef("int", [object_typedef],
+int_typedef = StdTypeDef("int",
     __new__ = newmethod(descr__new__),
     )

Modified: pypy/trunk/src/pypy/objspace/std/itertype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/itertype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/itertype.py	Fri Jun 11 20:01:13 2004
@@ -1,10 +1,6 @@
-"""
-Reviewed 03-06-22
-"""
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 # ____________________________________________________________
 
-iter_typedef = StdTypeDef("sequence-iterator", [object_typedef],
+iter_typedef = StdTypeDef("sequence-iterator",
     )

Modified: pypy/trunk/src/pypy/objspace/std/listtype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/listtype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/listtype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 from sys import maxint
 
 list_append = MultiMethod('append', 2)
@@ -20,7 +19,7 @@
 
 # ____________________________________________________________
 
-list_typedef = StdTypeDef("list", [object_typedef],
+list_typedef = StdTypeDef("list",
     __new__ = newmethod(descr__new__),
     )
 list_typedef.registermethods(globals())

Modified: pypy/trunk/src/pypy/objspace/std/longtype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/longtype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/longtype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 def descr__new__(space, w_longtype, w_value=None):
     from longobject import W_LongObject
@@ -11,6 +10,6 @@
 
 # ____________________________________________________________
 
-long_typedef = StdTypeDef("long", [object_typedef],
+long_typedef = StdTypeDef("long",
     __new__ = newmethod(descr__new__),
     )

Modified: pypy/trunk/src/pypy/objspace/std/nonetype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/nonetype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/nonetype.py	Fri Jun 11 20:01:13 2004
@@ -1,8 +1,7 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 
 # ____________________________________________________________
 
-none_typedef = StdTypeDef("NoneType", [object_typedef],
+none_typedef = StdTypeDef("NoneType",
     )

Modified: pypy/trunk/src/pypy/objspace/std/objecttype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/objecttype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/objecttype.py	Fri Jun 11 20:01:13 2004
@@ -31,7 +31,7 @@
 
 # ____________________________________________________________
 
-object_typedef = StdTypeDef("object", [],
+object_typedef = StdTypeDef("object",
     __getattribute__ = gateway.interp2app(Object.descr__getattribute__.im_func),
     __setattr__ = gateway.interp2app(Object.descr__setattr__.im_func),
     __delattr__ = gateway.interp2app(Object.descr__delattr__.im_func),

Modified: pypy/trunk/src/pypy/objspace/std/objspace.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/objspace.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/objspace.py	Fri Jun 11 20:01:13 2004
@@ -182,8 +182,6 @@
                         }
 
         # types
-        from pypy.objspace.std.objecttype import object_typedef
-        self.object_typedef = object_typedef
         self.types_w = {}
         for typedef in self.standard_types():
             w_type = self.gettypeobject(typedef)

Modified: pypy/trunk/src/pypy/objspace/std/slicetype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/slicetype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/slicetype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 from pypy.objspace.std.register_all import register_all
 from pypy.interpreter.error import OperationError
 
@@ -102,7 +101,7 @@
 
 # ____________________________________________________________
 
-slice_typedef = StdTypeDef("slice", [object_typedef],
+slice_typedef = StdTypeDef("slice",
     __new__ = newmethod(descr__new__),
     start = attrproperty_w('w_start'),
     stop  = attrproperty_w('w_stop'),

Modified: pypy/trunk/src/pypy/objspace/std/stdtypedef.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/stdtypedef.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/stdtypedef.py	Fri Jun 11 20:01:13 2004
@@ -11,20 +11,23 @@
 
 class StdTypeDef(TypeDef):
 
-    def __init__(self, name, bases, **rawdict):
-        TypeDef.__init__(self, name, **rawdict)
-        self.bases = bases
+    def __init__(self, __name, __base=None, **rawdict):
+        TypeDef.__init__(self, __name, __base, **rawdict)
         self.local_multimethods = []
 
     def registermethods(self, namespace):
         self.local_multimethods += hack_out_multimethods(namespace)
 
-    def mro(self, space):
-        assert len(self.bases) <= 1
-        if self.bases:
-            return [self] + self.bases[0].mro(space)
-        else:
-            return [self]
+def issubtypedef(a, b):
+    from pypy.objspace.std.objecttype import object_typedef
+    if b is object_typedef:
+        return True
+    while a is not b:
+        a = a.base
+        if a is None:
+            return False
+    return True
+
 
 def newmethod(descr_new):
     # this is turned into a static method by the constructor of W_TypeObject.
@@ -39,6 +42,7 @@
 def buildtypeobject(typedef, space):
     # build a W_TypeObject from this StdTypeDef
     from pypy.objspace.std.typeobject import W_TypeObject
+    from pypy.objspace.std.objecttype import object_typedef
 
     w = space.wrap
     rawdict = typedef.rawdict.copy()
@@ -55,10 +59,13 @@
             assert name not in rawdict, 'name clash: %s in %s_typedef' % (
                 name, typedef.name)
             rawdict[name] = fn
-        bases_w = [space.gettypeobject(basedef) for basedef in typedef.bases]
+
+    # compute the bases
+    if typedef is object_typedef:
+        bases_w = []
     else:
-        from pypy.objspace.std.objecttype import object_typedef
-        bases_w = [space.gettypeobject(object_typedef)]
+        base = typedef.base or object_typedef
+        bases_w = [space.gettypeobject(base)]
 
     # wrap everything
     dict_w = {}

Modified: pypy/trunk/src/pypy/objspace/std/stringtype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/stringtype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/stringtype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 str_join    = MultiMethod('join', 2)
 str_split   = MultiMethod('split', 3, defaults=(None,-1))
@@ -45,7 +44,7 @@
 
 # ____________________________________________________________
 
-str_typedef = StdTypeDef("str", [object_typedef],
+str_typedef = StdTypeDef("str",
     __new__ = newmethod(descr__new__),
     )
 str_typedef.registermethods(globals())

Modified: pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/test/test_typeobject.py	Fri Jun 11 20:01:13 2004
@@ -89,5 +89,14 @@
         self.assertEquals(f.__call__(a=1, b=2, c=3), ((), {"a": 1, "b": 2,
                                                            "c": 3}))
 
+    def test_multipleinheritance_fail(self):
+        try:
+            class A(int, dict):
+                pass
+        except TypeError:
+            pass
+        else:
+            raise AssertionError, "this multiple inheritance should fail"
+
 if __name__ == '__main__':
     testit.main()

Modified: pypy/trunk/src/pypy/objspace/std/tupletype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/tupletype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/tupletype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 
 def descr__new__(space, w_tupletype, w_items=None):
@@ -12,6 +11,6 @@
 
 # ____________________________________________________________
 
-tuple_typedef = StdTypeDef("tuple", [object_typedef],
+tuple_typedef = StdTypeDef("tuple",
     __new__ = newmethod(descr__new__),
     )

Modified: pypy/trunk/src/pypy/objspace/std/typeobject.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/typeobject.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/typeobject.py	Fri Jun 11 20:01:13 2004
@@ -1,6 +1,7 @@
 from pypy.objspace.std.objspace import *
 from pypy.interpreter.function import Function, StaticMethod
 from pypy.interpreter.typedef import attrproperty_w
+from pypy.objspace.std.stdtypedef import issubtypedef
 
 class W_TypeObject(W_Object):
     from pypy.objspace.std.typetype import type_typedef as typedef
@@ -16,19 +17,31 @@
         if overridetypedef is not None:
             w_self.instancetypedef = overridetypedef
         else:
-            # find the most specific typedef
-            longest_mro = [space.object_typedef]
-            for w_base in bases_w:
-                mro = w_base.instancetypedef.mro(space)
-                if len(mro) > len(longest_mro):
-                    longest_mro = mro
-            # check that it is a sub-typedef of all other ones
-            for w_base in bases_w:
-                if w_base.instancetypedef not in longest_mro:
+##            # find the most specific typedef
+##            longest_mro = [space.object_typedef]
+##            for w_base in bases_w:
+##                mro = w_base.instancetypedef.mro(space)
+##                if len(mro) > len(longest_mro):
+##                    longest_mro = mro
+##            # check that it is a sub-typedef of all other ones
+##            for w_base in bases_w:
+##                if w_base.instancetypedef not in longest_mro:
+##                    raise OperationError(space.w_TypeError,
+##                                space.wrap("instance layout conflicts in "
+##                                                    "multiple inheritance"))
+##            w_self.instancetypedef = longest_mro[0]
+            
+            assert bases_w  # typetype.descr__new__ should take care that there
+                            # is always at least one base
+            instancetypedef = bases_w[0].instancetypedef
+            w_self.instancetypedef = instancetypedef
+            # check that the remaining bases don't have an incompatible 'layout'
+            for w_base in bases_w[1:]:
+                if not issubtypedef(instancetypedef, w_base.instancetypedef):
                     raise OperationError(space.w_TypeError,
                                 space.wrap("instance layout conflicts in "
                                                     "multiple inheritance"))
-            w_self.instancetypedef = longest_mro[0]
+
             nd = False
             for w_base in bases_w:
                 if w_base.needs_new_dict:

Modified: pypy/trunk/src/pypy/objspace/std/typetype.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/std/typetype.py	(original)
+++ pypy/trunk/src/pypy/objspace/std/typetype.py	Fri Jun 11 20:01:13 2004
@@ -1,5 +1,4 @@
 from pypy.objspace.std.stdtypedef import *
-from pypy.objspace.std.objecttype import object_typedef
 
 
 def descr__new__(space, w_typetype, w_name, w_bases, w_dict):
@@ -34,7 +33,7 @@
 
 # ____________________________________________________________
 
-type_typedef = StdTypeDef("type", [object_typedef],
+type_typedef = StdTypeDef("type",
     __new__ = newmethod(descr__new__),
     __name__ = attrproperty('name'),
     __bases__ = GetSetProperty(descr__bases),

Modified: pypy/trunk/src/pypy/objspace/trivial.py
==============================================================================
--- pypy/trunk/src/pypy/objspace/trivial.py	(original)
+++ pypy/trunk/src/pypy/objspace/trivial.py	Fri Jun 11 20:01:13 2004
@@ -150,43 +150,41 @@
         except AttributeError:
             from pypy.interpreter.gateway import interp2app
             
-            # make the base first (assuming single inheritance)
-            mro = typedef.mro(self)
-            if len(mro) > 1:
-                bases = (self.hackwrapperclass(mro[1]),)
+            # make the base first
+            if typedef.base:
+                bases = (self.hackwrapperclass(typedef.base),)
             else:
                 bases = (CPyWrapper,)
             # make the class dict with descriptors redirecting to the ones
             # in rawdict
             descrdict = {'__internalpypytypedef__': typedef}
-            if typedef.name != 'object':
-                for descrname, descr in typedef.rawdict.items():
-                    if isinstance(descr, interp2app):
-                        def make_stuff(descr=descr, descrname=descrname, space=self):
-                            def stuff(w_obj, *args, **kwds):
-                                fn = descr.get_function(space)
-                                try:
-                                    return fn.descr_function_call(w_obj, *args, **kwds)
-                                except OperationError, e:
-                                    if not hasattr(e.w_type, 'originalex'):
-                                        raise # XXX
-                                    # XXX normalize ...
-                                    #if isinstance(e.w_value, e.w_type):
-                                    raise e.w_type.originalex(repr(e.w_value)) # e.w_value) 
-                            return stuff
-                        descrdict[descrname] = make_stuff()
-                    else:
-                        # more generally, defining a property
-                        def fget(w_obj, descr=descr, space=self):
-                            w_descr = space.wrap(descr)
-                            return space.get(w_descr, w_obj, space.type(w_obj))
-                        def fset(w_obj, w_value, descr=descr, space=self):
-                            w_descr = space.wrap(descr)
-                            return space.set(w_descr, w_obj, w_value)
-                        def fdel(w_obj, descr=descr, space=self):
-                            w_descr = space.wrap(descr)
-                            return space.set(w_descr, w_obj)
-                        descrdict[descrname] = property(fget, fset, fdel)
+            for descrname, descr in typedef.rawdict.items():
+                if isinstance(descr, interp2app):
+                    def make_stuff(descr=descr, descrname=descrname, space=self):
+                        def stuff(w_obj, *args, **kwds):
+                            fn = descr.get_function(space)
+                            try:
+                                return fn.descr_function_call(w_obj, *args, **kwds)
+                            except OperationError, e:
+                                if not hasattr(e.w_type, 'originalex'):
+                                    raise # XXX
+                                # XXX normalize ...
+                                #if isinstance(e.w_value, e.w_type):
+                                raise e.w_type.originalex(repr(e.w_value)) # e.w_value) 
+                        return stuff
+                    descrdict[descrname] = make_stuff()
+                else:
+                    # more generally, defining a property
+                    def fget(w_obj, descr=descr, space=self):
+                        w_descr = space.wrap(descr)
+                        return space.get(w_descr, w_obj, space.type(w_obj))
+                    def fset(w_obj, w_value, descr=descr, space=self):
+                        w_descr = space.wrap(descr)
+                        return space.set(w_descr, w_obj, w_value)
+                    def fdel(w_obj, descr=descr, space=self):
+                        w_descr = space.wrap(descr)
+                        return space.set(w_descr, w_obj)
+                    descrdict[descrname] = property(fget, fset, fdel)
             cls = type('CPyWrapped '+typedef.name, bases, descrdict)
             typedef.trivialwrapperclass = cls
             return cls
@@ -441,9 +439,12 @@
         assert not isinstance(w_obj, BaseWrappable)
         if isinstance(w_obj, CPyWrapper):
             typedef = type(w_obj).__internalpypytypedef__
-            for basedef in typedef.mro(space):
-                if name in basedef.rawdict:
-                    return space.wrap(basedef.rawdict[name])
+            while typedef is not None:
+                if name in typedef.rawdict:
+                    return space.wrap(typedef.rawdict[name])
+                typedef = typedef.base
+            if name in space.object_typedef.rawdict:
+                return space.wrap(space.object_typedef.rawdict[name])
             return None 
         else:
             for cls in w_obj.__class__.__mro__:



More information about the Pypy-commit mailing list