[pypy-commit] pypy cppyy-packaging: improve consistency PyPy <-> CPython

wlav pypy.commits at gmail.com
Thu Oct 12 16:04:48 EDT 2017


Author: Wim Lavrijsen <WLavrijsen at lbl.gov>
Branch: cppyy-packaging
Changeset: r92742:eb3d59d5546b
Date: 2017-10-12 12:54 -0700
http://bitbucket.org/pypy/pypy/changeset/eb3d59d5546b/

Log:	improve consistency PyPy <-> CPython

diff --git a/pypy/module/_cppyy/capi/loadable_capi.py b/pypy/module/_cppyy/capi/loadable_capi.py
--- a/pypy/module/_cppyy/capi/loadable_capi.py
+++ b/pypy/module/_cppyy/capi/loadable_capi.py
@@ -217,7 +217,8 @@
             'method_req_args'          : ([c_scope, c_index],         c_int),
             'method_arg_type'          : ([c_scope, c_index, c_int],  c_ccharp),
             'method_arg_default'       : ([c_scope, c_index, c_int],  c_ccharp),
-            'method_signature'         : ([c_scope, c_index],         c_ccharp),
+            'method_signature'         : ([c_scope, c_index, c_int],  c_ccharp),
+            'method_prototype'         : ([c_scope, c_index, c_int],  c_ccharp),
 
             'method_is_template'       : ([c_scope, c_index],         c_int),
             'method_num_template_args' : ([c_scope, c_index],         c_int),
@@ -498,9 +499,12 @@
 def c_method_arg_default(space, cppscope, index, arg_index):
     args = [_ArgH(cppscope.handle), _ArgL(index), _ArgL(arg_index)]
     return charp2str_free(space, call_capi(space, 'method_arg_default', args))
-def c_method_signature(space, cppscope, index):
-    args = [_ArgH(cppscope.handle), _ArgL(index)]
+def c_method_signature(space, cppscope, index, show_formalargs=True):
+    args = [_ArgH(cppscope.handle), _ArgL(index), _ArgL(show_formalargs)]
     return charp2str_free(space, call_capi(space, 'method_signature', args))
+def c_method_prototype(space, cppscope, index, show_formalargs=True):
+    args = [_ArgH(cppscope.handle), _ArgL(index), _ArgL(show_formalargs)]
+    return charp2str_free(space, call_capi(space, 'method_prototype', args))
 
 def c_method_is_template(space, cppscope, index):
     args = [_ArgH(cppscope.handle), _ArgL(index)]
diff --git a/pypy/module/_cppyy/include/capi.h b/pypy/module/_cppyy/include/capi.h
--- a/pypy/module/_cppyy/include/capi.h
+++ b/pypy/module/_cppyy/include/capi.h
@@ -19,14 +19,15 @@
     RPY_EXTERN
     int cppyy_num_scopes(cppyy_scope_t parent);
     RPY_EXTERN
-    char* cppyy_scope_name(cppyy_scope_t parent, int iscope);
-
+    char* cppyy_scope_name(cppyy_scope_t parent, cppyy_index_t iscope);
     RPY_EXTERN
     char* cppyy_resolve_name(const char* cppitem_name);
     RPY_EXTERN
     cppyy_scope_t cppyy_get_scope(const char* scope_name);
     RPY_EXTERN
     cppyy_type_t cppyy_actual_class(cppyy_type_t klass, cppyy_object_t obj);
+    RPY_EXTERN
+    size_t cppyy_size_of(cppyy_type_t klass);
 
     /* memory management ------------------------------------------------------ */
     RPY_EXTERN
@@ -120,6 +121,8 @@
     RPY_EXTERN
     char* cppyy_method_name(cppyy_scope_t scope, cppyy_index_t idx);
     RPY_EXTERN
+    char* cppyy_method_mangled_name(cppyy_scope_t scope, cppyy_index_t idx);
+    RPY_EXTERN
     char* cppyy_method_result_type(cppyy_scope_t scope, cppyy_index_t idx);
     RPY_EXTERN
     int cppyy_method_num_args(cppyy_scope_t scope, cppyy_index_t idx);
@@ -130,7 +133,9 @@
     RPY_EXTERN
     char* cppyy_method_arg_default(cppyy_scope_t scope, cppyy_index_t idx, int arg_index);
     RPY_EXTERN
-    char* cppyy_method_signature(cppyy_scope_t scope, cppyy_index_t idx);
+    char* cppyy_method_signature(cppyy_scope_t scope, cppyy_index_t idx, int show_formalargs);
+    RPY_EXTERN
+    char* cppyy_method_prototype(cppyy_scope_t scope, cppyy_index_t idx, int show_formalargs);
 
     RPY_EXTERN
     int cppyy_method_is_template(cppyy_scope_t scope, cppyy_index_t idx);
@@ -147,8 +152,12 @@
 
     /* method properties ------------------------------------------------------ */
     RPY_EXTERN
+    int cppyy_is_publicmethod(cppyy_type_t type, cppyy_index_t idx);
+    RPY_EXTERN
     int cppyy_is_constructor(cppyy_type_t type, cppyy_index_t idx);
     RPY_EXTERN
+    int cppyy_is_destructor(cppyy_type_t type, cppyy_index_t idx);
+    RPY_EXTERN
     int cppyy_is_staticmethod(cppyy_type_t type, cppyy_index_t idx);
 
     /* data member reflection information ------------------------------------- */
diff --git a/pypy/module/_cppyy/interp_cppyy.py b/pypy/module/_cppyy/interp_cppyy.py
--- a/pypy/module/_cppyy/interp_cppyy.py
+++ b/pypy/module/_cppyy/interp_cppyy.py
@@ -194,8 +194,13 @@
         # check number of given arguments against required (== total - defaults)
         args_expected = len(self.arg_defs)
         args_given = len(args_w)
-        if args_expected < args_given or args_given < self.args_required:
-            raise oefmt(self.space.w_TypeError, "wrong number of arguments")
+
+        if args_given < self.args_required:
+            raise oefmt(self.space.w_TypeError,
+                "takes at least %d arguments (%d given)", self.args_required, args_given)
+        elif args_expected < args_given:
+            raise oefmt(self.space.w_TypeError,
+                "takes at most %d arguments (%d given)", args_expected, args_given)
 
         # initial setup of converters, executors, and libffi (if available)
         if self.converters is None:
@@ -381,8 +386,11 @@
             conv.free_argument(self.space, rffi.cast(capi.C_OBJECT, arg_i), loc_i)
         capi.c_deallocate_function_args(self.space, args)
 
-    def signature(self):
-        return capi.c_method_signature(self.space, self.scope, self.index)
+    def signature(self, show_formalargs=True):
+        return capi.c_method_signature(self.space, self.scope, self.index, show_formalargs)
+
+    def prototype(self, show_formalargs=True):
+        return capi.c_method_prototype(self.space, self.scope, self.index, show_formalargs)
 
     def priority(self):
         total_arg_priority = 0
@@ -396,7 +404,7 @@
             lltype.free(self.cif_descr, flavor='raw')
 
     def __repr__(self):
-        return "CPPMethod: %s" % self.signature()
+        return "CPPMethod: %s" % self.prototype()
 
     def _freeze_(self):
         assert 0, "you should never have a pre-built instance of this!"
@@ -412,7 +420,7 @@
         return capi.C_NULL_OBJECT
 
     def __repr__(self):
-        return "CPPFunction: %s" % self.signature()
+        return "CPPFunction: %s" % self.prototype()
 
 
 class CPPTemplatedCall(CPPMethod):
@@ -445,7 +453,7 @@
         return CPPMethod.call(self, cppthis, args_w)
 
     def __repr__(self):
-        return "CPPTemplatedCall: %s" % self.signature()
+        return "CPPTemplatedCall: %s" % self.prototype()
 
 
 class CPPConstructor(CPPMethod):
@@ -467,7 +475,7 @@
         return CPPMethod.call(self, cppthis, args_w)
 
     def __repr__(self):
-        return "CPPConstructor: %s" % self.signature()
+        return "CPPConstructor: %s" % self.prototype()
 
 
 class CPPSetItem(CPPMethod):
@@ -554,12 +562,12 @@
                     w_exc_type = e.w_type
                 elif all_same_type and not e.match(self.space, w_exc_type):
                     all_same_type = False
-                errmsg += '\n  '+cppyyfunc.signature()+' =>\n'
+                errmsg += '\n  '+cppyyfunc.prototype()+' =>\n'
                 errmsg += '    '+e.errorstr(self.space)
             except Exception as e:
                 # can not special case this for non-overloaded functions as we anyway need an
                 # OperationError error down from here
-                errmsg += '\n  '+cppyyfunc.signature()+' =>\n'
+                errmsg += '\n  '+cppyyfunc.prototype()+' =>\n'
                 errmsg += '    Exception: '+str(e)
 
         if all_same_type and w_exc_type is not None:
@@ -567,20 +575,20 @@
         else:
             raise OperationError(self.space.w_TypeError, self.space.newtext(errmsg))
 
-    def signature(self):
-        sig = self.functions[0].signature()
+    def prototype(self):
+        sig = self.functions[0].prototype()
         for i in range(1, len(self.functions)):
-            sig += '\n'+self.functions[i].signature()
+            sig += '\n'+self.functions[i].prototype()
         return self.space.newtext(sig)
 
     def __repr__(self):
-        return "W_CPPOverload(%s)" % [f.signature() for f in self.functions]
+        return "W_CPPOverload(%s)" % [f.prototype() for f in self.functions]
 
 W_CPPOverload.typedef = TypeDef(
     'CPPOverload',
     is_static = interp2app(W_CPPOverload.is_static),
     call = interp2app(W_CPPOverload.call),
-    signature = interp2app(W_CPPOverload.signature),
+    prototype = interp2app(W_CPPOverload.prototype),
 )
 
 
@@ -609,13 +617,13 @@
             memory_regulator.register(cppinstance)
 
     def __repr__(self):
-        return "W_CPPConstructorOverload(%s)" % [f.signature() for f in self.functions]
+        return "W_CPPConstructorOverload(%s)" % [f.prototype() for f in self.functions]
 
 W_CPPConstructorOverload.typedef = TypeDef(
     'CPPConstructorOverload',
     is_static = interp2app(W_CPPConstructorOverload.is_static),
     call = interp2app(W_CPPConstructorOverload.call),
-    signature = interp2app(W_CPPOverload.signature),
+    prototype = interp2app(W_CPPOverload.prototype),
 )
 
 
@@ -760,7 +768,7 @@
         overload = self.get_overload(name)
         sig = '(%s)' % signature
         for f in overload.functions:
-            if 0 < f.signature().find(sig):
+            if f.signature(False) == sig:
                 return W_CPPOverload(self.space, self, [f])
         raise oefmt(self.space.w_LookupError, "no overload matches signature")
 
diff --git a/pypy/module/_cppyy/pythonify.py b/pypy/module/_cppyy/pythonify.py
--- a/pypy/module/_cppyy/pythonify.py
+++ b/pypy/module/_cppyy/pythonify.py
@@ -116,7 +116,7 @@
     def function(*args):
         return cppol.call(None, *args)
     function.__name__ = func_name
-    function.__doc__ = cppol.signature()
+    function.__doc__ = cppol.prototype()
     return staticmethod(function)
 
 
@@ -165,7 +165,7 @@
     def method(self, *args):
         return cppol.call(self, *args)
     method.__name__ = meth_name
-    method.__doc__ = cppol.signature()
+    method.__doc__ = cppol.prototype()
     return method
 
 def make_cppclass(scope, cl_name, decl):
diff --git a/pypy/module/_cppyy/test/test_fragile.py b/pypy/module/_cppyy/test/test_fragile.py
--- a/pypy/module/_cppyy/test/test_fragile.py
+++ b/pypy/module/_cppyy/test/test_fragile.py
@@ -163,20 +163,23 @@
             assert 0
         except TypeError as e:
             assert "fragile::D::check()" in str(e)
-            assert "TypeError: wrong number of arguments" in str(e)
+            assert "TypeError: takes at most 0 arguments (1 given)" in str(e)
+            assert "TypeError: takes at least 2 arguments (1 given)" in str(e)
 
         try:
             d.overload(None)      # raises TypeError
             assert 0
         except TypeError as e:
+            # TODO: pypy-c does not indicate which argument failed to convert, CPython does
+            # likewise there are still minor differences in descriptiveness of messages
             assert "fragile::D::overload()" in str(e)
-            assert "TypeError: wrong number of arguments" in str(e)
+            assert "TypeError: takes at most 0 arguments (1 given)" in str(e)
             assert "fragile::D::overload(fragile::no_such_class*)" in str(e)
-            assert "TypeError: no converter available for 'fragile::no_such_class*'" in str(e)
-            assert "fragile::D::overload(char, int)" in str(e)
-            assert "TypeError: expected string, got NoneType object" in str(e)
-            assert "fragile::D::overload(int, fragile::no_such_class*)" in str(e)
-            assert "TypeError: expected integer, got NoneType object" in str(e)
+            #assert "no converter available for 'fragile::no_such_class*'" in str(e)
+            assert "void fragile::D::overload(char, int i = 0)" in str(e)
+            #assert "char or small int type expected" in str(e)
+            assert "void fragile::D::overload(int, fragile::no_such_class* p = 0)" in str(e)
+            #assert "int/long conversion expects an integer object" in str(e)
 
         j = fragile.J()
         assert fragile.J.method1.__doc__ == j.method1.__doc__


More information about the pypy-commit mailing list