]> granicus.if.org Git - python/commitdiff
Added two new functions to conveniently call functions/methods from C.
authorFred Drake <fdrake@acm.org>
Fri, 26 Oct 2001 16:21:32 +0000 (16:21 +0000)
committerFred Drake <fdrake@acm.org>
Fri, 26 Oct 2001 16:21:32 +0000 (16:21 +0000)
PyObject_CallFunctionObArgs() and PyObject_CallMethodObArgs() have the
advantage that no format strings need to be parsed.  The CallMethod
variant also avoids creating a new string object in order to retrieve
a method from an object as well.

Include/abstract.h
Objects/abstract.c

index 351149db6f25f7cf87643907202bc956339036e3..0d44f6d224e6d4b6a38a59fb692ea6dbb02d3dd6 100644 (file)
@@ -299,7 +299,6 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
                                         PyObject *args, PyObject *kw);
 
        /*
-
         Call a callable Python object, callable_object, with
         arguments and keywords arguments.  The 'args' argument can not be
         NULL, but the 'kw' argument can be NULL.
@@ -310,7 +309,6 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
                                                PyObject *args);
 
        /*
-
         Call a callable Python object, callable_object, with
         arguments given by the tuple, args.  If no arguments are
         needed, then args may be NULL.  Returns the result of the
@@ -343,11 +341,31 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/
         arguments are provided. Returns the result of the call on
         success, or NULL on failure.  This is the equivalent of the
         Python expression: o.method(args).
+       */
+
 
-         Note that Special method names, such as "__add__",
-        "__getitem__", and so on are not supported. The specific
-        abstract-object routines for these must be used.
+     DL_IMPORT(PyObject *) PyObject_CallFunctionObArgs(PyObject *callable,
+                                                       ...);
 
+       /*
+        Call a callable Python object, callable_object, with a
+        variable number of C arguments.  The C arguments are provided
+        as PyObject * values; 'n' specifies the number of arguments
+        present.  Returns the result of the call on success, or NULL
+        on failure.  This is the equivalent of the Python expression:
+        apply(o,args).
+       */
+
+
+     DL_IMPORT(PyObject *) PyObject_CallMethodObArgs(PyObject *o,
+                                                     PyObject *m, ...);
+
+       /*
+        Call the method named m of object o with a variable number of
+        C arguments.  The C arguments are provided as PyObject * values;
+        'n' specifies the number of arguments present.  Returns the
+        result of the call on success, or NULL on failure.  This is the
+        equivalent of the Python expression: o.method(args).
        */
 
 
index 6b9201ba36151c3b498bf04dc2cd3fc739a2e4d3..003c9a362d964928659194bd4c1c972695e0fdf7 100644 (file)
@@ -1758,6 +1758,82 @@ PyObject_CallMethod(PyObject *o, char *name, char *format, ...)
 }
 
 
+static PyObject *
+obargs_mktuple(va_list va)
+{
+       int i, n = 0;
+       va_list countva;
+       PyObject *result, *tmp;
+
+#ifdef VA_LIST_IS_ARRAY
+       memcpy(countva, va, sizeof(va_list));
+#else
+       countva = va;
+#endif
+
+       while (((PyObject *)va_arg(countva, PyObject *)) != NULL)
+               ++n;
+       result = PyTuple_New(n);
+       if (result != NULL && n > 0) {
+               for (i = 0; i < n; ++i) {
+                       tmp = (PyObject *)va_arg(va, PyObject *);
+                       PyTuple_SET_ITEM(result, i, tmp);
+                       Py_INCREF(tmp);
+               }
+       }
+       return result;
+}
+
+PyObject *
+PyObject_CallMethodObArgs(PyObject *callable, PyObject *name, ...)
+{
+       PyObject *args, *tmp;
+       va_list vargs;
+
+       if (callable == NULL || name == NULL)
+               return null_error();
+
+       callable = PyObject_GetAttr(callable, name);
+       if (callable == NULL)
+               return NULL;
+
+       /* count the args */
+       va_start(vargs, name);
+       args = obargs_mktuple(vargs);
+       va_end(vargs);
+       if (args == NULL) {
+               Py_DECREF(callable);
+               return NULL;
+       }
+       tmp = PyObject_Call(callable, args, NULL);
+       Py_DECREF(args);
+       Py_DECREF(callable);
+
+       return tmp;
+}
+
+PyObject *
+PyObject_CallFunctionObArgs(PyObject *callable, ...)
+{
+       PyObject *args, *tmp;
+       va_list vargs;
+
+       if (callable == NULL)
+               return null_error();
+
+       /* count the args */
+       va_start(vargs, callable);
+       args = obargs_mktuple(vargs);
+       va_end(vargs);
+       if (args == NULL)
+               return NULL;
+       tmp = PyObject_Call(callable, args, NULL);
+       Py_DECREF(args);
+
+       return tmp;
+}
+
+
 /* isinstance(), issubclass() */
 
 static PyObject *