a3784c8617523d80f9935f20f1503f8fc09566c7
[platform/upstream/python-gobject.git] / gi / pygtype.c
1 /* -*- Mode: C; c-basic-offset: 4 -*-
2  * pygtk- Python bindings for the GTK toolkit.
3  * Copyright (C) 1998-2003  James Henstridge
4  *
5  *   pygtype.c: glue code to wrap the GType code.
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
19  */
20
21 #ifdef HAVE_CONFIG_H
22 #  include <config.h>
23 #endif
24
25 #include <pyglib.h>
26
27 #include "pygobject-private.h"
28 #include "pygparamspec.h"
29 #include "pygtype.h"
30
31 #include "pygi-type.h"
32 #include "pygi-value.h"
33
34 /* -------------- __gtype__ objects ---------------------------- */
35
36 typedef struct {
37     PyObject_HEAD
38     GType type;
39 } PyGTypeWrapper;
40
41 PYGLIB_DEFINE_TYPE("gobject.GType", PyGTypeWrapper_Type, PyGTypeWrapper);
42
43 static PyObject*
44 pyg_type_wrapper_richcompare(PyObject *self, PyObject *other, int op)
45 {
46     if (Py_TYPE(self) == Py_TYPE(other) && Py_TYPE(self) == &PyGTypeWrapper_Type)
47         return _pyglib_generic_long_richcompare(((PyGTypeWrapper*)self)->type,
48                                                 ((PyGTypeWrapper*)other)->type,
49                                                 op);
50     else {
51         Py_INCREF(Py_NotImplemented);
52         return Py_NotImplemented;
53     }
54 }
55
56 static long
57 pyg_type_wrapper_hash(PyGTypeWrapper *self)
58 {
59     return (long)self->type;
60 }
61
62 static PyObject *
63 pyg_type_wrapper_repr(PyGTypeWrapper *self)
64 {
65     char buf[80];
66     const gchar *name = g_type_name(self->type);
67
68     g_snprintf(buf, sizeof(buf), "<GType %s (%lu)>",
69                name?name:"invalid", (unsigned long int) self->type);
70     return PYGLIB_PyUnicode_FromString(buf);
71 }
72
73 static void
74 pyg_type_wrapper_dealloc(PyGTypeWrapper *self)
75 {
76     PyObject_DEL(self);
77 }
78
79 static GQuark
80 _pyg_type_key(GType type) {
81     GQuark key;
82
83     if (g_type_is_a(type, G_TYPE_INTERFACE)) {
84         key = pyginterface_type_key;
85     } else if (g_type_is_a(type, G_TYPE_ENUM)) {
86         key = pygenum_class_key;
87     } else if (g_type_is_a(type, G_TYPE_FLAGS)) {
88         key = pygflags_class_key;
89     } else if (g_type_is_a(type, G_TYPE_POINTER)) {
90         key = pygpointer_class_key;
91     } else if (g_type_is_a(type, G_TYPE_BOXED)) {
92         key = pygboxed_type_key;
93     } else {
94         key = pygobject_class_key;
95     }
96
97     return key;
98 }
99
100 static PyObject *
101 _wrap_g_type_wrapper__get_pytype(PyGTypeWrapper *self, void *closure)
102 {
103     GQuark key;
104     PyObject *py_type;
105
106     key = _pyg_type_key(self->type);
107
108     py_type = g_type_get_qdata(self->type, key);
109     if (!py_type)
110       py_type = Py_None;
111
112     Py_INCREF(py_type);
113     return py_type;
114 }
115
116 static int
117 _wrap_g_type_wrapper__set_pytype(PyGTypeWrapper *self, PyObject* value, void *closure)
118 {
119     GQuark key;
120     PyObject *py_type;
121
122     key = _pyg_type_key(self->type);
123
124     py_type = g_type_get_qdata(self->type, key);
125     Py_CLEAR(py_type);
126     if (value == Py_None)
127         g_type_set_qdata(self->type, key, NULL);
128     else if (PyType_Check(value)) {
129         Py_INCREF(value);
130         g_type_set_qdata(self->type, key, value);
131     } else {
132         PyErr_SetString(PyExc_TypeError, "Value must be None or a type object");
133         return -1;
134     }
135
136     return 0;
137 }
138
139 static PyObject *
140 _wrap_g_type_wrapper__get_name(PyGTypeWrapper *self, void *closure)
141 {
142    const char *name = g_type_name(self->type);
143    return PYGLIB_PyUnicode_FromString(name ? name : "invalid");
144 }
145
146 static PyObject *
147 _wrap_g_type_wrapper__get_parent(PyGTypeWrapper *self, void *closure)
148 {
149    return pyg_type_wrapper_new(g_type_parent(self->type));
150 }
151
152 static PyObject *
153 _wrap_g_type_wrapper__get_fundamental(PyGTypeWrapper *self, void *closure)
154 {
155    return pyg_type_wrapper_new(g_type_fundamental(self->type));
156 }
157
158 static PyObject *
159 _wrap_g_type_wrapper__get_children(PyGTypeWrapper *self, void *closure)
160 {
161   guint n_children, i;
162   GType *children;
163   PyObject *retval;
164
165   children = g_type_children(self->type, &n_children);
166
167   retval = PyList_New(n_children);
168   for (i = 0; i < n_children; i++)
169       PyList_SetItem(retval, i, pyg_type_wrapper_new(children[i]));
170   g_free(children);
171
172   return retval;
173 }
174
175 static PyObject *
176 _wrap_g_type_wrapper__get_interfaces(PyGTypeWrapper *self, void *closure)
177 {
178   guint n_interfaces, i;
179   GType *interfaces;
180   PyObject *retval;
181
182   interfaces = g_type_interfaces(self->type, &n_interfaces);
183
184   retval = PyList_New(n_interfaces);
185   for (i = 0; i < n_interfaces; i++)
186       PyList_SetItem(retval, i, pyg_type_wrapper_new(interfaces[i]));
187   g_free(interfaces);
188
189   return retval;
190 }
191
192 static PyObject *
193 _wrap_g_type_wrapper__get_depth(PyGTypeWrapper *self, void *closure)
194 {
195   return PYGLIB_PyLong_FromLong(g_type_depth(self->type));
196 }
197
198 static PyGetSetDef _PyGTypeWrapper_getsets[] = {
199     { "pytype", (getter)_wrap_g_type_wrapper__get_pytype, (setter)_wrap_g_type_wrapper__set_pytype },
200     { "name",  (getter)_wrap_g_type_wrapper__get_name, (setter)0 },
201     { "fundamental",  (getter)_wrap_g_type_wrapper__get_fundamental, (setter)0 },
202     { "parent",  (getter)_wrap_g_type_wrapper__get_parent, (setter)0 },
203     { "children",  (getter)_wrap_g_type_wrapper__get_children, (setter)0 },
204     { "interfaces",  (getter)_wrap_g_type_wrapper__get_interfaces, (setter)0 },
205     { "depth",  (getter)_wrap_g_type_wrapper__get_depth, (setter)0 },
206     { NULL, (getter)0, (setter)0 }
207 };
208
209 static PyObject*
210 _wrap_g_type_is_interface(PyGTypeWrapper *self)
211 {
212     return PyBool_FromLong(G_TYPE_IS_INTERFACE(self->type));
213 }
214
215 static PyObject*
216 _wrap_g_type_is_classed(PyGTypeWrapper *self)
217 {
218     return PyBool_FromLong(G_TYPE_IS_CLASSED(self->type));
219 }
220
221 static PyObject*
222 _wrap_g_type_is_instantiatable(PyGTypeWrapper *self)
223 {
224     return PyBool_FromLong(G_TYPE_IS_INSTANTIATABLE(self->type));
225 }
226
227 static PyObject*
228 _wrap_g_type_is_derivable(PyGTypeWrapper *self)
229 {
230     return PyBool_FromLong(G_TYPE_IS_DERIVABLE(self->type));
231 }
232
233 static PyObject*
234 _wrap_g_type_is_deep_derivable(PyGTypeWrapper *self)
235 {
236     return PyBool_FromLong(G_TYPE_IS_DEEP_DERIVABLE(self->type));
237 }
238
239 static PyObject*
240 _wrap_g_type_is_abstract(PyGTypeWrapper *self)
241 {
242     return PyBool_FromLong(G_TYPE_IS_ABSTRACT(self->type));
243 }
244
245 static PyObject*
246 _wrap_g_type_is_value_abstract(PyGTypeWrapper *self)
247 {
248     return PyBool_FromLong(G_TYPE_IS_VALUE_ABSTRACT(self->type));
249 }
250
251 static PyObject*
252 _wrap_g_type_is_value_type(PyGTypeWrapper *self)
253 {
254     return PyBool_FromLong(G_TYPE_IS_VALUE_TYPE(self->type));
255 }
256
257 static PyObject*
258 _wrap_g_type_has_value_table(PyGTypeWrapper *self)
259 {
260     return PyBool_FromLong(G_TYPE_HAS_VALUE_TABLE(self->type));
261 }
262
263 static PyObject*
264 _wrap_g_type_from_name(PyGTypeWrapper *_, PyObject *args)
265 {
266     char *type_name;
267     GType type;
268
269     if (!PyArg_ParseTuple(args, "s:GType.from_name", &type_name))
270         return NULL;
271
272     type = g_type_from_name(type_name);
273     if (type == 0) {
274         PyErr_SetString(PyExc_RuntimeError, "unknown type name");
275         return NULL;
276     }
277
278     return pyg_type_wrapper_new(type);
279 }
280
281 static PyObject*
282 _wrap_g_type_is_a(PyGTypeWrapper *self, PyObject *args)
283 {
284     PyObject *gparent;
285     GType parent;
286
287     if (!PyArg_ParseTuple(args, "O:GType.is_a", &gparent))
288         return NULL;
289     else if ((parent = pyg_type_from_object(gparent)) == 0)
290         return NULL;
291
292     return PyBool_FromLong(g_type_is_a(self->type, parent));
293 }
294
295 static PyMethodDef _PyGTypeWrapper_methods[] = {
296     { "is_interface", (PyCFunction)_wrap_g_type_is_interface, METH_NOARGS },
297     { "is_classed", (PyCFunction)_wrap_g_type_is_classed, METH_NOARGS },
298     { "is_instantiatable", (PyCFunction)_wrap_g_type_is_instantiatable, METH_NOARGS },
299     { "is_derivable", (PyCFunction)_wrap_g_type_is_derivable, METH_NOARGS },
300     { "is_deep_derivable", (PyCFunction)_wrap_g_type_is_deep_derivable, METH_NOARGS },
301     { "is_abstract", (PyCFunction)_wrap_g_type_is_abstract, METH_NOARGS },
302     { "is_value_abstract", (PyCFunction)_wrap_g_type_is_value_abstract, METH_NOARGS },
303     { "is_value_type", (PyCFunction)_wrap_g_type_is_value_type, METH_NOARGS },
304     { "has_value_table", (PyCFunction)_wrap_g_type_has_value_table, METH_NOARGS },
305     { "from_name", (PyCFunction)_wrap_g_type_from_name, METH_VARARGS | METH_STATIC },
306     { "is_a", (PyCFunction)_wrap_g_type_is_a, METH_VARARGS },
307     { NULL,  0, 0 }
308 };
309
310 static int
311 pyg_type_wrapper_init(PyGTypeWrapper *self, PyObject *args, PyObject *kwargs)
312 {
313     static char *kwlist[] = { "object", NULL };
314     PyObject *py_object;
315     GType type;
316
317     if (!PyArg_ParseTupleAndKeywords(args, kwargs,
318                                      "O:GType.__init__",
319                                      kwlist, &py_object))
320         return -1;
321
322     if (!(type = pyg_type_from_object(py_object)))
323         return -1;
324
325     self->type = type;
326
327     return 0;
328 }
329
330 /**
331  * pyg_type_wrapper_new:
332  * type: a GType
333  *
334  * Creates a Python wrapper for a GType.
335  *
336  * Returns: the Python wrapper.
337  */
338 PyObject *
339 pyg_type_wrapper_new(GType type)
340 {
341     PyGTypeWrapper *self;
342
343     self = (PyGTypeWrapper *)PyObject_NEW(PyGTypeWrapper,
344                                           &PyGTypeWrapper_Type);
345     if (self == NULL)
346         return NULL;
347
348     self->type = type;
349     return (PyObject *)self;
350 }
351
352 /**
353  * pyg_type_from_object_strict:
354  * obj: a Python object
355  * strict: if set to TRUE, raises an exception if it can't perform the
356  *         conversion
357  *
358  * converts a python object to a GType.  If strict is set, raises an 
359  * exception if it can't perform the conversion, otherwise returns
360  * PY_TYPE_OBJECT.
361  *
362  * Returns: the corresponding GType, or 0 on error.
363  */
364
365 GType
366 pyg_type_from_object_strict(PyObject *obj, gboolean strict)
367 {
368     PyObject *gtype;
369     GType type;
370
371     /* NULL check */
372     if (!obj) {
373         PyErr_SetString(PyExc_TypeError, "can't get type from NULL object");
374         return 0;
375     }
376
377     /* map some standard types to primitive GTypes ... */
378     if (obj == Py_None)
379         return G_TYPE_NONE;
380     if (PyType_Check(obj)) {
381         PyTypeObject *tp = (PyTypeObject *)obj;
382
383         if (tp == &PYGLIB_PyLong_Type)
384             return G_TYPE_INT;
385         else if (tp == &PyBool_Type)
386             return G_TYPE_BOOLEAN;
387         else if (tp == &PyLong_Type)
388             return G_TYPE_LONG;
389         else if (tp == &PyFloat_Type)
390             return G_TYPE_DOUBLE;
391         else if (tp == &PYGLIB_PyUnicode_Type)
392             return G_TYPE_STRING;
393         else if (tp == &PyBaseObject_Type)
394             return PY_TYPE_OBJECT;
395     }
396
397     if (Py_TYPE(obj) == &PyGTypeWrapper_Type) {
398         return ((PyGTypeWrapper *)obj)->type;
399     }
400
401     /* handle strings */
402     if (PYGLIB_PyUnicode_Check(obj)) {
403         gchar *name = PYGLIB_PyUnicode_AsString(obj);
404
405         type = g_type_from_name(name);
406         if (type != 0) {
407             return type;
408         }
409     }
410
411     /* finally, look for a __gtype__ attribute on the object */
412     gtype = PyObject_GetAttrString(obj, "__gtype__");
413
414     if (gtype) {
415         if (Py_TYPE(gtype) == &PyGTypeWrapper_Type) {
416             type = ((PyGTypeWrapper *)gtype)->type;
417             Py_DECREF(gtype);
418             return type;
419         }
420         Py_DECREF(gtype);
421     }
422
423     PyErr_Clear();
424
425     /* Some API like those that take GValues can hold a python object as
426      * a pointer.  This is potentially dangerous becuase everything is 
427      * passed in as a PyObject so we can't actually type check it.  Only
428      * fallback to PY_TYPE_OBJECT if strict checking is disabled
429      */
430     if (!strict)
431         return PY_TYPE_OBJECT;
432
433     PyErr_SetString(PyExc_TypeError, "could not get typecode from object");
434     return 0;
435 }
436
437 /**
438  * pyg_type_from_object:
439  * obj: a Python object
440  *
441  * converts a python object to a GType.  Raises an exception if it
442  * can't perform the conversion.
443  *
444  * Returns: the corresponding GType, or 0 on error.
445  */
446 GType
447 pyg_type_from_object(PyObject *obj)
448 {
449     /* Legacy call always defaults to strict type checking */
450     return pyg_type_from_object_strict(obj, TRUE);
451 }
452
453 /**
454  * pyg_enum_get_value:
455  * @enum_type: the GType of the flag.
456  * @obj: a Python object representing the flag value
457  * @val: a pointer to the location to store the integer representation of the flag.
458  *
459  * Converts a Python object to the integer equivalent.  The conversion
460  * will depend on the type of the Python object.  If the object is an
461  * integer, it is passed through directly.  If it is a string, it will
462  * be treated as a full or short enum name as defined in the GType.
463  *
464  * Returns: 0 on success or -1 on failure
465  */
466 gint
467 pyg_enum_get_value(GType enum_type, PyObject *obj, gint *val)
468 {
469     GEnumClass *eclass = NULL;
470     gint res = -1;
471
472     g_return_val_if_fail(val != NULL, -1);
473     if (!obj) {
474         *val = 0;
475         res = 0;
476     } else if (PYGLIB_PyLong_Check(obj)) {
477         *val = PYGLIB_PyLong_AsLong(obj);
478         res = 0;
479
480         if (PyObject_TypeCheck(obj, &PyGEnum_Type) && ((PyGEnum *) obj)->gtype != enum_type) {
481             g_warning("expected enumeration type %s, but got %s instead",
482                       g_type_name(enum_type),
483                       g_type_name(((PyGEnum *) obj)->gtype));
484         }
485     /* Dumb code duplication, but probably not worth it to have yet another macro. */
486     } else if (PyLong_Check(obj)) {
487         *val = PyLong_AsLong(obj);
488         res = 0;
489
490         if (PyObject_TypeCheck(obj, &PyGEnum_Type) && ((PyGEnum *) obj)->gtype != enum_type) {
491             g_warning("expected enumeration type %s, but got %s instead",
492                       g_type_name(enum_type),
493                       g_type_name(((PyGEnum *) obj)->gtype));
494         }
495     } else if (PYGLIB_PyUnicode_Check(obj)) {
496         GEnumValue *info;
497         char *str = PYGLIB_PyUnicode_AsString(obj);
498
499         if (enum_type != G_TYPE_NONE)
500             eclass = G_ENUM_CLASS(g_type_class_ref(enum_type));
501         else {
502             PyErr_SetString(PyExc_TypeError, "could not convert string to enum because there is no GType associated to look up the value");
503             res = -1;
504         }
505         info = g_enum_get_value_by_name(eclass, str);
506         g_type_class_unref(eclass);
507
508         if (!info)
509             info = g_enum_get_value_by_nick(eclass, str);
510         if (info) {
511             *val = info->value;
512             res = 0;
513         } else {
514             PyErr_SetString(PyExc_TypeError, "could not convert string");
515             res = -1;
516         }
517     } else {
518         PyErr_SetString(PyExc_TypeError,"enum values must be strings or ints");
519         res = -1;
520     }
521     return res;
522 }
523
524 /**
525  * pyg_flags_get_value:
526  * @flag_type: the GType of the flag.
527  * @obj: a Python object representing the flag value
528  * @val: a pointer to the location to store the integer representation of the flag.
529  *
530  * Converts a Python object to the integer equivalent.  The conversion
531  * will depend on the type of the Python object.  If the object is an
532  * integer, it is passed through directly.  If it is a string, it will
533  * be treated as a full or short flag name as defined in the GType.
534  * If it is a tuple, then the items are treated as strings and ORed
535  * together.
536  *
537  * Returns: 0 on success or -1 on failure
538  */
539 gint
540 pyg_flags_get_value(GType flag_type, PyObject *obj, guint *val)
541 {
542     GFlagsClass *fclass = NULL;
543     gint res = -1;
544
545     g_return_val_if_fail(val != NULL, -1);
546     if (!obj) {
547         *val = 0;
548         res = 0;
549     } else if (PYGLIB_PyLong_Check(obj)) {
550         *val = PYGLIB_PyLong_AsUnsignedLong(obj);
551         res = 0;
552     } else if (PyLong_Check(obj)) {
553         *val = PyLong_AsLongLong(obj);
554         res = 0;
555     } else if (PYGLIB_PyUnicode_Check(obj)) {
556         GFlagsValue *info;
557         char *str = PYGLIB_PyUnicode_AsString(obj);
558
559         if (flag_type != G_TYPE_NONE)
560             fclass = G_FLAGS_CLASS(g_type_class_ref(flag_type));
561         else {
562             PyErr_SetString(PyExc_TypeError, "could not convert string to flag because there is no GType associated to look up the value");
563             res = -1;
564         }
565         info = g_flags_get_value_by_name(fclass, str);
566         g_type_class_unref(fclass);
567
568         if (!info)
569             info = g_flags_get_value_by_nick(fclass, str);
570         if (info) {
571             *val = info->value;
572             res = 0;
573         } else {
574             PyErr_SetString(PyExc_TypeError, "could not convert string");
575             res = -1;
576         }
577     } else if (PyTuple_Check(obj)) {
578         int i, len;
579
580         len = PyTuple_Size(obj);
581         *val = 0;
582         res = 0;
583
584         if (flag_type != G_TYPE_NONE)
585             fclass = G_FLAGS_CLASS(g_type_class_ref(flag_type));
586         else {
587             PyErr_SetString(PyExc_TypeError, "could not convert string to flag because there is no GType associated to look up the value");
588             res = -1;
589         }
590
591         for (i = 0; i < len; i++) {
592             PyObject *item = PyTuple_GetItem(obj, i);
593             char *str = PYGLIB_PyUnicode_AsString(item);
594             GFlagsValue *info = g_flags_get_value_by_name(fclass, str);
595
596             if (!info)
597                 info = g_flags_get_value_by_nick(fclass, str);
598             if (info) {
599                 *val |= info->value;
600             } else {
601                 PyErr_SetString(PyExc_TypeError, "could not convert string");
602                 res = -1;
603                 break;
604             }
605         }
606         g_type_class_unref(fclass);
607     } else {
608         PyErr_SetString(PyExc_TypeError,
609                         "flag values must be strings, ints, longs, or tuples");
610         res = -1;
611     }
612     return res;
613 }
614
615 static GQuark pyg_type_marshal_key = 0;
616
617 PyGTypeMarshal *
618 pyg_type_lookup(GType type)
619 {
620     GType       ptype = type;
621     PyGTypeMarshal      *tm = NULL;
622
623     /* recursively lookup types */
624     while (ptype) {
625         pygi_type_import_by_g_type (ptype);
626         if ((tm = g_type_get_qdata(ptype, pyg_type_marshal_key)) != NULL)
627             break;
628         ptype = g_type_parent(ptype);
629     }
630     return tm;
631 }
632
633 /**
634  * pyg_register_gtype_custom:
635  * @gtype: the GType for the new type
636  * @from_func: a function to convert GValues to Python objects
637  * @to_func: a function to convert Python objects to GValues
638  *
639  * In order to handle specific conversion of gboxed types or new
640  * fundamental types, you may use this function to register conversion
641  * handlers.
642  */
643
644 void
645 pyg_register_gtype_custom(GType gtype,
646                           fromvaluefunc from_func,
647                           tovaluefunc to_func)
648 {
649     PyGTypeMarshal *tm;
650
651     if (!pyg_type_marshal_key)
652         pyg_type_marshal_key = g_quark_from_static_string("PyGType::marshal");
653
654     tm = g_new(PyGTypeMarshal, 1);
655     tm->fromvalue = from_func;
656     tm->tovalue = to_func;
657     g_type_set_qdata(gtype, pyg_type_marshal_key, tm);
658 }
659
660 /* -------------- PyGClosure ----------------- */
661
662 static void
663 pyg_closure_invalidate(gpointer data, GClosure *closure)
664 {
665     PyGClosure *pc = (PyGClosure *)closure;
666     PyGILState_STATE state;
667
668     state = pyglib_gil_state_ensure();
669     Py_XDECREF(pc->callback);
670     Py_XDECREF(pc->extra_args);
671     Py_XDECREF(pc->swap_data);
672     pyglib_gil_state_release(state);
673
674     pc->callback = NULL;
675     pc->extra_args = NULL;
676     pc->swap_data = NULL;
677 }
678
679 static void
680 pyg_closure_marshal(GClosure *closure,
681                     GValue *return_value,
682                     guint n_param_values,
683                     const GValue *param_values,
684                     gpointer invocation_hint,
685                     gpointer marshal_data)
686 {
687     PyGILState_STATE state;
688     PyGClosure *pc = (PyGClosure *)closure;
689     PyObject *params, *ret;
690     guint i;
691
692     state = pyglib_gil_state_ensure();
693
694     /* construct Python tuple for the parameter values */
695     params = PyTuple_New(n_param_values);
696     for (i = 0; i < n_param_values; i++) {
697         /* swap in a different initial data for connect_object() */
698         if (i == 0 && G_CCLOSURE_SWAP_DATA(closure)) {
699             g_return_if_fail(pc->swap_data != NULL);
700             Py_INCREF(pc->swap_data);
701             PyTuple_SetItem(params, 0, pc->swap_data);
702         } else {
703             PyObject *item = pyg_value_as_pyobject(&param_values[i], FALSE);
704
705             /* error condition */
706             if (!item) {
707             if (!PyErr_Occurred ())
708                 PyErr_SetString (PyExc_TypeError,
709                                  "can't convert parameter to desired type");
710
711             if (pc->exception_handler)
712                 pc->exception_handler (return_value, n_param_values, param_values);
713             else
714                 PyErr_Print();
715
716             goto out;
717             }
718             PyTuple_SetItem(params, i, item);
719         }
720     }
721     /* params passed to function may have extra arguments */
722     if (pc->extra_args) {
723         PyObject *tuple = params;
724         params = PySequence_Concat(tuple, pc->extra_args);
725         Py_DECREF(tuple);
726     }
727     ret = PyObject_CallObject(pc->callback, params);
728     if (ret == NULL) {
729         if (pc->exception_handler)
730             pc->exception_handler(return_value, n_param_values, param_values);
731         else
732             PyErr_Print();
733         goto out;
734     }
735
736     if (G_IS_VALUE(return_value) && pyg_value_from_pyobject(return_value, ret) != 0) {
737         /* If we already have an exception set, use that, otherwise set a
738          * generic one */
739         if (!PyErr_Occurred())
740             PyErr_SetString(PyExc_TypeError,
741                             "can't convert return value to desired type");
742
743         if (pc->exception_handler)
744             pc->exception_handler(return_value, n_param_values, param_values);
745         else
746             PyErr_Print();
747     }
748     Py_DECREF(ret);
749
750  out:
751     Py_DECREF(params);
752     pyglib_gil_state_release(state);
753 }
754
755 /**
756  * pyg_closure_new:
757  * callback: a Python callable object
758  * extra_args: a tuple of extra arguments, or None/NULL.
759  * swap_data: an alternative python object to pass first.
760  *
761  * Creates a GClosure wrapping a Python callable and optionally a set
762  * of additional function arguments.  This is needed to attach python
763  * handlers to signals, for instance.
764  *
765  * Returns: the new closure.
766  */
767 GClosure *
768 pyg_closure_new(PyObject *callback, PyObject *extra_args, PyObject *swap_data)
769 {
770     GClosure *closure;
771
772     g_return_val_if_fail(callback != NULL, NULL);
773     closure = g_closure_new_simple(sizeof(PyGClosure), NULL);
774     g_closure_add_invalidate_notifier(closure, NULL, pyg_closure_invalidate);
775     g_closure_set_marshal(closure, pyg_closure_marshal);
776     Py_INCREF(callback);
777     ((PyGClosure *)closure)->callback = callback;
778     if (extra_args && extra_args != Py_None) {
779         Py_INCREF(extra_args);
780         if (!PyTuple_Check(extra_args)) {
781             PyObject *tmp = PyTuple_New(1);
782             PyTuple_SetItem(tmp, 0, extra_args);
783             extra_args = tmp;
784         }
785         ((PyGClosure *)closure)->extra_args = extra_args;
786     }
787     if (swap_data) {
788         Py_INCREF(swap_data);
789         ((PyGClosure *)closure)->swap_data = swap_data;
790         closure->derivative_flag = TRUE;
791     }
792     return closure;
793 }
794
795 /**
796  * pyg_closure_set_exception_handler:
797  * @closure: a closure created with pyg_closure_new()
798  * @handler: the handler to call when an exception occurs or NULL for none
799  *
800  * Sets the handler to call when an exception occurs during closure invocation.
801  * The handler is responsible for providing a proper return value to the
802  * closure invocation. If @handler is %NULL, the default handler will be used.
803  * The default handler prints the exception to stderr and doesn't touch the
804  * closure's return value.
805  */
806 void
807 pyg_closure_set_exception_handler(GClosure *closure,
808                                   PyClosureExceptionHandler handler)
809 {
810     PyGClosure *pygclosure;
811
812     g_return_if_fail(closure != NULL);
813
814     pygclosure = (PyGClosure *)closure;
815     pygclosure->exception_handler = handler;
816 }
817 /* -------------- PySignalClassClosure ----------------- */
818 /* a closure used for the `class closure' of a signal.  As this gets
819  * all the info from the first argument to the closure and the
820  * invocation hint, we can have a single closure that handles all
821  * class closure cases.  We call a method by the name of the signal
822  * with "do_" prepended.
823  *
824  *  We also remove the first argument from the * param list, as it is
825  *  the instance object, which is passed * implicitly to the method
826  *  object. */
827
828 static void
829 pyg_signal_class_closure_marshal(GClosure *closure,
830                                  GValue *return_value,
831                                  guint n_param_values,
832                                  const GValue *param_values,
833                                  gpointer invocation_hint,
834                                  gpointer marshal_data)
835 {
836     PyGILState_STATE state;
837     GObject *object;
838     PyObject *object_wrapper;
839     GSignalInvocationHint *hint = (GSignalInvocationHint *)invocation_hint;
840     gchar *method_name, *tmp;
841     PyObject *method;
842     PyObject *params, *ret;
843     guint i, len;
844
845     state = pyglib_gil_state_ensure();
846
847     g_return_if_fail(invocation_hint != NULL);
848     /* get the object passed as the first argument to the closure */
849     object = g_value_get_object(&param_values[0]);
850     g_return_if_fail(object != NULL && G_IS_OBJECT(object));
851
852     /* get the wrapper for this object */
853     object_wrapper = pygobject_new(object);
854     g_return_if_fail(object_wrapper != NULL);
855
856     /* construct method name for this class closure */
857     method_name = g_strconcat("do_", g_signal_name(hint->signal_id), NULL);
858
859     /* convert dashes to underscores.  For some reason, g_signal_name
860      * seems to convert all the underscores in the signal name to
861        dashes??? */
862     for (tmp = method_name; *tmp != '\0'; tmp++)
863         if (*tmp == '-') *tmp = '_';
864
865     method = PyObject_GetAttrString(object_wrapper, method_name);
866     g_free(method_name);
867
868     if (!method) {
869         PyErr_Clear();
870         Py_DECREF(object_wrapper);
871         pyglib_gil_state_release(state);
872         return;
873     }
874     Py_DECREF(object_wrapper);
875
876     /* construct Python tuple for the parameter values; don't copy boxed values
877        initially because we'll check after the call to see if a copy is needed. */
878     params = PyTuple_New(n_param_values - 1);
879     for (i = 1; i < n_param_values; i++) {
880         PyObject *item = pyg_value_as_pyobject(&param_values[i], FALSE);
881
882         /* error condition */
883         if (!item) {
884             Py_DECREF(params);
885             pyglib_gil_state_release(state);
886             return;
887         }
888         PyTuple_SetItem(params, i - 1, item);
889     }
890
891     ret = PyObject_CallObject(method, params);
892
893     /* Copy boxed values if others ref them, this needs to be done regardless of
894        exception status. */
895     len = PyTuple_Size(params);
896     for (i = 0; i < len; i++) {
897         PyObject *item = PyTuple_GetItem(params, i);
898         if (item != NULL && PyObject_TypeCheck(item, &PyGBoxed_Type)
899             && item->ob_refcnt != 1) {
900             PyGBoxed* boxed_item = (PyGBoxed*)item;
901             if (!boxed_item->free_on_dealloc) {
902                 gpointer boxed_ptr = pyg_boxed_get_ptr (boxed_item);
903                 pyg_boxed_set_ptr (boxed_item, g_boxed_copy (boxed_item->gtype, boxed_ptr));
904                 boxed_item->free_on_dealloc = TRUE;
905             }
906         }
907     }
908
909     if (ret == NULL) {
910         PyErr_Print();
911         Py_DECREF(method);
912         Py_DECREF(params);
913         pyglib_gil_state_release(state);
914         return;
915     }
916     Py_DECREF(method);
917     Py_DECREF(params);
918     if (G_IS_VALUE(return_value))
919         pyg_value_from_pyobject(return_value, ret);
920     Py_DECREF(ret);
921     pyglib_gil_state_release(state);
922 }
923
924 /**
925  * pyg_signal_class_closure_get:
926  *
927  * Returns the GClosure used for the class closure of signals.  When
928  * called, it will invoke the method do_signalname (for the signal
929  * "signalname").
930  *
931  * Returns: the closure.
932  */
933 GClosure *
934 pyg_signal_class_closure_get(void)
935 {
936     static GClosure *closure;
937
938     if (closure == NULL) {
939         closure = g_closure_new_simple(sizeof(GClosure), NULL);
940         g_closure_set_marshal(closure, pyg_signal_class_closure_marshal);
941
942         g_closure_ref(closure);
943         g_closure_sink(closure);
944     }
945     return closure;
946 }
947
948 GClosure *
949 gclosure_from_pyfunc(PyGObject *object, PyObject *func)
950 {
951     GSList *l;
952     PyGObjectData *inst_data;
953     inst_data = pyg_object_peek_inst_data(object->obj);
954     if (inst_data) {
955         for (l = inst_data->closures; l; l = l->next) {
956             PyGClosure *pyclosure = l->data;
957             int res = PyObject_RichCompareBool(pyclosure->callback, func, Py_EQ);
958             if (res == -1) {
959                 PyErr_Clear(); /* Is there anything else to do? */
960             } else if (res) {
961                 return (GClosure*)pyclosure;
962             }
963         }
964     }
965     return NULL;
966 }
967
968 /* ----- __doc__ descriptor for GObject and GInterface ----- */
969
970 static void
971 object_doc_dealloc(PyObject *self)
972 {
973     PyObject_FREE(self);
974 }
975
976 /* append information about signals of a particular gtype */
977 static void
978 add_signal_docs(GType gtype, GString *string)
979 {
980     GTypeClass *class = NULL;
981     guint *signal_ids, n_ids = 0, i;
982
983     if (G_TYPE_IS_CLASSED(gtype))
984         class = g_type_class_ref(gtype);
985     signal_ids = g_signal_list_ids(gtype, &n_ids);
986
987     if (n_ids > 0) {
988         g_string_append_printf(string, "Signals from %s:\n",
989                                g_type_name(gtype));
990
991         for (i = 0; i < n_ids; i++) {
992             GSignalQuery query;
993             guint j;
994
995             g_signal_query(signal_ids[i], &query);
996
997             g_string_append(string, "  ");
998             g_string_append(string, query.signal_name);
999             g_string_append(string, " (");
1000             for (j = 0; j < query.n_params; j++) {
1001                 g_string_append(string, g_type_name(query.param_types[j]));
1002                 if (j != query.n_params - 1)
1003                     g_string_append(string, ", ");
1004             }
1005             g_string_append(string, ")");
1006             if (query.return_type && query.return_type != G_TYPE_NONE) {
1007                 g_string_append(string, " -> ");
1008                 g_string_append(string, g_type_name(query.return_type));
1009             }
1010             g_string_append(string, "\n");
1011         }
1012         g_free(signal_ids);
1013         g_string_append(string, "\n");
1014     }
1015     if (class)
1016         g_type_class_unref(class);
1017 }
1018
1019 static void
1020 add_property_docs(GType gtype, GString *string)
1021 {
1022     GObjectClass *class;
1023     GParamSpec **props;
1024     guint n_props = 0, i;
1025     gboolean has_prop = FALSE;
1026     G_CONST_RETURN gchar *blurb=NULL;
1027
1028     class = g_type_class_ref(gtype);
1029     props = g_object_class_list_properties(class, &n_props);
1030
1031     for (i = 0; i < n_props; i++) {
1032         if (props[i]->owner_type != gtype)
1033             continue; /* these are from a parent type */
1034
1035         /* print out the heading first */
1036         if (!has_prop) {
1037             g_string_append_printf(string, "Properties from %s:\n",
1038                                    g_type_name(gtype));
1039             has_prop = TRUE;
1040         }
1041         g_string_append_printf(string, "  %s -> %s: %s\n",
1042                                g_param_spec_get_name(props[i]),
1043                                g_type_name(props[i]->value_type),
1044                                g_param_spec_get_nick(props[i]));
1045
1046         /* g_string_append_printf crashes on win32 if the third
1047            argument is NULL. */
1048         blurb=g_param_spec_get_blurb(props[i]);
1049         if (blurb)
1050             g_string_append_printf(string, "    %s\n",blurb);
1051     }
1052     g_free(props);
1053     if (has_prop)
1054         g_string_append(string, "\n");
1055     g_type_class_unref(class);
1056 }
1057
1058 static PyObject *
1059 object_doc_descr_get(PyObject *self, PyObject *obj, PyObject *type)
1060 {
1061     GType gtype = 0;
1062     GString *string;
1063     PyObject *pystring;
1064
1065     if (obj && pygobject_check(obj, &PyGObject_Type)) {
1066         gtype = G_OBJECT_TYPE(pygobject_get(obj));
1067         if (!gtype)
1068             PyErr_SetString(PyExc_RuntimeError, "could not get object type");
1069     } else {
1070         gtype = pyg_type_from_object(type);
1071     }
1072     if (!gtype)
1073         return NULL;
1074
1075     string = g_string_new_len(NULL, 512);
1076
1077     if (g_type_is_a(gtype, G_TYPE_INTERFACE))
1078         g_string_append_printf(string, "Interface %s\n\n", g_type_name(gtype));
1079     else if (g_type_is_a(gtype, G_TYPE_OBJECT))
1080         g_string_append_printf(string, "Object %s\n\n", g_type_name(gtype));
1081     else
1082         g_string_append_printf(string, "%s\n\n", g_type_name(gtype));
1083
1084     if (((PyTypeObject *) type)->tp_doc)
1085         g_string_append_printf(string, "%s\n\n", ((PyTypeObject *) type)->tp_doc);
1086
1087     if (g_type_is_a(gtype, G_TYPE_OBJECT)) {
1088         GType parent = G_TYPE_OBJECT;
1089         GArray *parents = g_array_new(FALSE, FALSE, sizeof(GType));
1090         int iparent;
1091
1092         while (parent) {
1093             g_array_append_val(parents, parent);
1094             parent = g_type_next_base(gtype, parent);
1095         }
1096
1097         for (iparent = parents->len - 1; iparent >= 0; --iparent) {
1098             GType *interfaces;
1099             guint n_interfaces, i;
1100
1101             parent = g_array_index(parents, GType, iparent);
1102             add_signal_docs(parent, string);
1103             add_property_docs(parent, string);
1104
1105             /* add docs for implemented interfaces */
1106             interfaces = g_type_interfaces(parent, &n_interfaces);
1107             for (i = 0; i < n_interfaces; i++)
1108                 add_signal_docs(interfaces[i], string);
1109             g_free(interfaces);
1110         }
1111         g_array_free(parents, TRUE);
1112     }
1113
1114     pystring = PYGLIB_PyUnicode_FromStringAndSize(string->str, string->len);
1115     g_string_free(string, TRUE);
1116     return pystring;
1117 }
1118
1119 PYGLIB_DEFINE_TYPE("gobject.GObject.__doc__", PyGObjectDoc_Type, PyObject);
1120
1121 /**
1122  * pyg_object_descr_doc_get:
1123  *
1124  * Returns an object intended to be the __doc__ attribute of GObject
1125  * wrappers.  When read in the context of the object it will return
1126  * some documentation about the signals and properties of the object.
1127  *
1128  * Returns: the descriptor.
1129  */
1130 PyObject *
1131 pyg_object_descr_doc_get(void)
1132 {
1133     static PyObject *doc_descr = NULL;
1134
1135     if (!doc_descr) {
1136         Py_TYPE(&PyGObjectDoc_Type) = &PyType_Type;
1137         if (PyType_Ready(&PyGObjectDoc_Type))
1138             return NULL;
1139
1140         doc_descr = PyObject_NEW(PyObject, &PyGObjectDoc_Type);
1141         if (doc_descr == NULL)
1142             return NULL;
1143     }
1144     return doc_descr;
1145 }
1146
1147
1148 /**
1149  * pyg_pyobj_to_unichar_conv:
1150  *
1151  * Converts PyObject value to a unichar and write result to memory
1152  * pointed to by ptr.  Follows the calling convention of a ParseArgs
1153  * converter (O& format specifier) so it may be used to convert function
1154  * arguments.
1155  *
1156  * Returns: 1 if the conversion succeeds and 0 otherwise.  If the conversion
1157  *          did not succeesd, a Python exception is raised
1158  */
1159 int pyg_pyobj_to_unichar_conv(PyObject* py_obj, void* ptr)
1160 {
1161     gunichar* u = ptr;
1162     const Py_UNICODE* uni_buffer;
1163     PyObject* tmp_uni = NULL;
1164
1165     if (PyUnicode_Check(py_obj)) {
1166         tmp_uni = py_obj;
1167         Py_INCREF(tmp_uni);
1168     }
1169     else {
1170         tmp_uni = PyUnicode_FromObject(py_obj);
1171         if (tmp_uni == NULL)
1172             goto failure;
1173     }
1174
1175     if ( PyUnicode_GetSize(tmp_uni) != 1) {
1176         PyErr_SetString(PyExc_ValueError, "unicode character value must be 1 character uniode string");
1177         goto failure;
1178     }
1179     uni_buffer = PyUnicode_AsUnicode(tmp_uni);
1180     if ( uni_buffer == NULL)
1181         goto failure;
1182     *u = uni_buffer[0];
1183
1184     Py_DECREF(tmp_uni);
1185     return 1;
1186
1187   failure:
1188     Py_XDECREF(tmp_uni);
1189     return 0;
1190 }
1191
1192 gboolean
1193 pyg_gtype_is_custom(GType gtype)
1194 {
1195     return g_type_get_qdata (gtype, pygobject_custom_key) != NULL;
1196 }
1197
1198 void
1199 pygobject_type_register_types(PyObject *d)
1200 {
1201     PyGTypeWrapper_Type.tp_dealloc = (destructor)pyg_type_wrapper_dealloc;
1202     PyGTypeWrapper_Type.tp_richcompare = pyg_type_wrapper_richcompare;
1203     PyGTypeWrapper_Type.tp_repr = (reprfunc)pyg_type_wrapper_repr;
1204     PyGTypeWrapper_Type.tp_hash = (hashfunc)pyg_type_wrapper_hash;
1205     PyGTypeWrapper_Type.tp_flags = Py_TPFLAGS_DEFAULT;
1206     PyGTypeWrapper_Type.tp_methods = _PyGTypeWrapper_methods;
1207     PyGTypeWrapper_Type.tp_getset = _PyGTypeWrapper_getsets;
1208     PyGTypeWrapper_Type.tp_init = (initproc)pyg_type_wrapper_init;
1209     PYGLIB_REGISTER_TYPE(d, PyGTypeWrapper_Type, "GType");
1210
1211     /* This type lazily registered in pyg_object_descr_doc_get */
1212     PyGObjectDoc_Type.tp_dealloc = (destructor)object_doc_dealloc;
1213     PyGObjectDoc_Type.tp_flags = Py_TPFLAGS_DEFAULT;
1214     PyGObjectDoc_Type.tp_descr_get = (descrgetfunc)object_doc_descr_get;
1215
1216     pyg_register_gtype_custom(G_TYPE_STRV,
1217                               pyg_strv_from_gvalue,
1218                               pyg_strv_to_gvalue);
1219 }