diff options
-rw-r--r-- | gtk/gdkevent.override | 46 | ||||
-rw-r--r-- | tests/test_gdkevent.py | 9 |
2 files changed, 35 insertions, 20 deletions
diff --git a/gtk/gdkevent.override b/gtk/gdkevent.override index 12ae0c1d..51c7423c 100644 --- a/gtk/gdkevent.override +++ b/gtk/gdkevent.override @@ -26,6 +26,11 @@ override-slot GdkEvent.tp_setattr PyErr_Format(PyExc_TypeError, "%s must be an int", attr); \ return -1; \ } +#define INT_OR_LONG_CHECK() \ + if (!PyInt_Check(value) && !PyLong_Check(value)) { \ + PyErr_Format(PyExc_TypeError, "%s must be an int or a long", attr); \ + return -1; \ + } #define FLOAT_CHECK() \ if (!PyFloat_Check(value)) { \ PyErr_Format(PyExc_TypeError, "%s must be a float", attr); \ @@ -84,8 +89,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) break; case GDK_MOTION_NOTIFY: /*GdkEventMotion motion*/ if (!strcmp(attr, "time")) { - INT_CHECK(); - event->motion.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->motion.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (attr[0] == 'x' && attr[1] == '\0') { FLOAT_CHECK(); @@ -124,8 +129,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) case GDK_3BUTTON_PRESS: /*GdkEventButton button*/ case GDK_BUTTON_RELEASE: /*GdkEventButton button*/ if (!strcmp(attr, "time")) { - INT_CHECK(); - event->button.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->button.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (attr[0] == 'x' && attr[1] == '\0') { FLOAT_CHECK(); @@ -162,8 +167,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) case GDK_KEY_PRESS: /*GdkEventKey key*/ case GDK_KEY_RELEASE: /*GdkEventKey key*/ if (!strcmp(attr, "time")) { - INT_CHECK(); - event->key.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->key.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (!strcmp(attr, "state")) { INT_CHECK(); @@ -204,8 +209,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) event->crossing.subwindow = g_object_ref(GDK_WINDOW(((PyGObject*)value)->obj)); return 0; } else if (!strcmp(attr, "time")) { - INT_CHECK(); - event->crossing.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->crossing.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (attr[0] == 'x' && attr[1] == '\0') { FLOAT_CHECK(); @@ -273,8 +278,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) PyErr_SetString(PyExc_TypeError, "atom is not writable"); return -1; } else if (!strcmp(attr, "time")) { - INT_CHECK(); - event->property.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->property.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (!strcmp(attr, "state")) { INT_CHECK(); @@ -299,8 +304,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) event->selection.requestor = PyInt_AsLong(value); return 0; } else if (!strcmp(attr, "time")) { - INT_CHECK(); - event->selection.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->selection.time = PyInt_AsUnsignedLongMask(value); return 0; } @@ -308,8 +313,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) case GDK_PROXIMITY_IN: /*GdkEventProximity proximity*/ case GDK_PROXIMITY_OUT: /*GdkEventProximity proximity*/ if (!strcmp(attr, "time")) { - INT_CHECK(); - event->proximity.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->proximity.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (!strcmp(attr, "device")) { PyErr_SetString(PyExc_TypeError, "device is not writable"); @@ -326,8 +331,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) PyErr_SetString(PyExc_TypeError, "context is not writable"); return -1; } else if (!strcmp(attr, "time")) { - INT_CHECK(); - event->dnd.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->dnd.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (!strcmp(attr, "x_root")) { FLOAT_CHECK(); @@ -370,8 +375,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) break; case GDK_SCROLL: /*GdkEventScroll scroll*/ if (!strcmp(attr, "time")) { - INT_CHECK(); - event->scroll.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->scroll.time = PyInt_AsUnsignedLongMask(value); return 0; } else if (attr[0] == 'x' && attr[1] == '\0') { FLOAT_CHECK(); @@ -435,8 +440,8 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) PyErr_SetString(PyExc_TypeError, "selection is not writable"); return -1; } else if (!strcmp(attr, "time")) { - INT_CHECK(); - event->owner_change.time = PyInt_AsLong(value); + INT_OR_LONG_CHECK(); + event->owner_change.time = PyInt_AsUnsignedLongMask(value); } else if (!strcmp(attr, "selection_time")) { INT_CHECK(); event->owner_change.selection_time = PyInt_AsLong(value); @@ -462,6 +467,7 @@ _wrap_gdk_event_tp_setattr(PyObject *self, char *attr, PyObject *value) return -1; } #undef INT_CHECK +#undef INT_OR_LONG_CHECK #undef FLOAT_CHECK #undef STRING_CHECK %% diff --git a/tests/test_gdkevent.py b/tests/test_gdkevent.py index 1721a9e4..741e8abf 100644 --- a/tests/test_gdkevent.py +++ b/tests/test_gdkevent.py @@ -18,5 +18,14 @@ class TestGdkEvent(unittest.TestCase): event.window = win2.window self.assertEqual(event.window, win2.window) + # Bug #408658. + def testEventTime(self): + event = gtk.gdk.Event(gtk.gdk.MOTION_NOTIFY) + event.time = 0x80000000 + + # According to GTK+ source files, 'time' field is always of + # 'guint32' type, so we must always have overflow here. + self.assert_(event.time == -0x80000000) + if __name__ == '__main__': unittest.main() |