After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 667983 - buffer overflow crash in function callback when a DBusProxy "g-properties-changed" signal is emitted
buffer overflow crash in function callback when a DBusProxy "g-properties-cha...
Status: VERIFIED FIXED
Product: pygobject
Classification: Bindings
Component: gio
3.2.x
Other Linux
: Normal major
: ---
Assigned To: Nobody's working on this now (help wanted and appreciated)
Python bindings maintainers
Depends on:
Blocks:
 
 
Reported: 2012-01-16 05:44 UTC by Nirbheek Chauhan
Modified: 2013-02-27 15:51 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
Test case to reproduce crash (740 bytes, text/plain)
2012-01-16 05:44 UTC, Nirbheek Chauhan
Details

Description Nirbheek Chauhan 2012-01-16 05:44:53 UTC
Created attachment 205333 [details]
Test case to reproduce crash 

Connecting a callback to the "g-properties-changed" DBusProxy signal causes
a buffer overflow after the signal is emitted.

I'm using pygobject-3.0.2, python-2.6.6, glib-2.31.6, gobject-introspection-1.30.0

A testcase for this is attached. Run rhythmbox, and change the song to see the crash. Note that the bug is not limited to just rhythmbox, since the C version of the same thing works just fine.

----------

*** buffer overflow detected ***: /usr/bin/python2.6 terminated
======= Backtrace: =========
/lib64/libc.so.6(__fortify_fail+0x3f)[0x7f2da37e43af]
/lib64/libc.so.6(+0xf0250)[0x7f2da37e2250]
/usr/lib64/python2.6/site-packages/gi/_gi.so(+0xd85c)[0x7f2da2bac85c]
/usr/lib64/python2.6/site-packages/gi/_gi.so(+0x11846)[0x7f2da2bb0846]
/usr/lib64/libgobject-2.0.so.0(g_closure_invoke+0x15b)[0x7f2da211b67b]
/usr/lib64/libgobject-2.0.so.0(+0x20801)[0x7f2da212b801]
/usr/lib64/libgobject-2.0.so.0(g_signal_emit_valist+0x60f)[0x7f2da21332ff]
/usr/lib64/libgobject-2.0.so.0(g_signal_emit+0x94)[0x7f2da21334e4]
/usr/lib64/libgio-2.0.so.0(+0xcdf19)[0x7f2da1754f19]
/usr/lib64/libgio-2.0.so.0(+0xbd06a)[0x7f2da174406a]
/usr/lib64/libglib-2.0.so.0(g_main_context_dispatch+0x171)[0x7f2da1a27d81]
/usr/lib64/libglib-2.0.so.0(+0x4a158)[0x7f2da1a28158]
/usr/lib64/libglib-2.0.so.0(g_main_loop_run+0x72)[0x7f2da1a28552]
/usr/lib64/python2.6/site-packages/gi/_glib/_glib.so(+0xaa9a)[0x7f2da104ea9a]
/usr/lib64/libpython2.6.so.1.0(PyEval_EvalFrameEx+0x4eef)[0x7f2da3d7522f]
/usr/lib64/libpython2.6.so.1.0(PyEval_EvalCodeEx+0x91a)[0x7f2da3d76eda]
/usr/lib64/libpython2.6.so.1.0(PyEval_EvalCode+0x36)[0x7f2da3d76fc6]
/usr/lib64/libpython2.6.so.1.0(+0xf3cad)[0x7f2da3d90cad]
/usr/lib64/libpython2.6.so.1.0(PyRun_FileExFlags+0x8a)[0x7f2da3d91a0a]
/usr/lib64/libpython2.6.so.1.0(PyRun_SimpleFileExFlags+0x1ee)[0x7f2da3d9255e]
/usr/lib64/libpython2.6.so.1.0(Py_Main+0xada)[0x7f2da3d9e9ba]
/lib64/libc.so.6(__libc_start_main+0x10f)[0x7f2da37140cf]
/usr/bin/python2.6[0x4008a9]
======= Memory map: ========
...
Comment 1 Nirbheek Chauhan 2012-02-02 15:02:07 UTC
It seems I forgot to paste the backtrace while filing this bug.

----
  • #0 *__GI_raise
    at ../nptl/sysdeps/unix/sysv/linux/raise.c line 64
  • #1 *__GI_abort
    at abort.c line 92
  • #2 __libc_message
    at ../sysdeps/unix/sysv/linux/libc_fatal.c line 186
  • #3 *__GI___fortify_fail
    at fortify_fail.c line 32
  • #4 *__GI___chk_fail
    at chk_fail.c line 29
  • #5 memcpy
    at /usr/include/bits/string3.h line 52
  • #6 _pygi_argument_to_object
    at pygi-argument.c line 1515
  • #7 pygi_signal_closure_marshal
    at pygi-signal-closure.c line 154
  • #8 g_closure_invoke
    at gclosure.c line 774
  • #9 signal_emit_unlocked_R
    at gsignal.c line 3302
  • #10 g_signal_emit_valist
    at gsignal.c line 3033
  • #11 g_signal_emit
    at gsignal.c line 3090
  • #12 on_properties_changed
    at gdbusproxy.c line 1055
  • #13 emit_signal_instance_in_idle_cb
    at gdbusconnection.c line 3676
  • #14 g_main_dispatch
    at gmain.c line 2513
  • #15 g_main_context_dispatch
    at gmain.c line 3050
  • #16 g_main_context_iterate
    at gmain.c line 3121
  • #17 g_main_loop_run
    at gmain.c line 3315
  • #18 _wrap_g_main_loop_run
    at pygmainloop.c line 331
  • #19 PyEval_EvalFrameEx
    from /usr/lib64/libpython2.6.so.1.0
  • #20 PyEval_EvalCodeEx
    from /usr/lib64/libpython2.6.so.1.0
  • #21 PyEval_EvalCode
    from /usr/lib64/libpython2.6.so.1.0
  • #22 ??
    from /usr/lib64/libpython2.6.so.1.0
  • #23 PyRun_FileExFlags
    from /usr/lib64/libpython2.6.so.1.0
  • #24 PyRun_SimpleFileExFlags
    from /usr/lib64/libpython2.6.so.1.0
  • #25 Py_Main
    from /usr/lib64/libpython2.6.so.1.0
  • #26 __libc_start_main
    at libc-start.c line 226
  • #27 _start

Comment 2 Nirbheek Chauhan 2012-02-06 17:02:28 UTC
All I can figure out is that in pygi_signal_closure_marshal():

a) "param_values[2]" is GStrv

(gdb) p g_type_name(param_values[2])
$148 = (const gchar *) 0x7ffff62de302 "GStrv"


b) but it has a corrupted value:

(gdb) p (GArray)param_values[2].data[0].v_pointer
$147 = {data = 0x7a2660 "", len = 134217728}


c) This causes a segfault in _pygi_argument_to_object():

array = arg->v_pointer;
[...]
memcpy (&item, &_g_array_index (array, GIArgument, i), item_size);


d) I was able to trace the origin of this back to g_signal_emit_valist():

(gdb) p (GArray)instance_and_params[2].data[0].v_pointer
$181 = {data = 0x7a2660 "", len = 134217728}


I have no idea how to take this through the va_args stuff in g_signal_emit, and hence I have no idea why param_values[2] is set to GStrv with a bad value.

The equivalent C code works perfectly, so I can't figure out why this is happening only with pygobject.

PS: my analysis of all this might be completely wrong.
Comment 3 Sebastian Pölsterl 2012-04-21 13:24:13 UTC
I followed your instructions using the test case you attached. With latest pygobject I don't see any crash, but the test case does not print anything as well. Could you please attach a test case the demonstrates the problem with latest pygobject?
Comment 4 Nirbheek Chauhan 2012-04-21 21:37:27 UTC
(In reply to comment #3)
> I followed your instructions using the test case you attached. With latest
> pygobject I don't see any crash, but the test case does not print anything as
> well. Could you please attach a test case the demonstrates the problem with
> latest pygobject?

Since it's a memory corruption bug, it sometimes carries on happily even when things are horribly wrong. One way to reproduce it more reliably (it makes no sense to me why this would work) is to do this:


 def playing_props_changed(*args, **kwargs):
+    print("test")
     print(args)


(Yes, add a dummy print in the signal handler)
Comment 5 Martin Pitt 2012-04-25 07:37:12 UTC
I can reproduce the crash with pygobject 3.2.0 and attached test case. The first time it prints the currently played song in RB, but when I change it, it crashes.
Comment 6 Martin Pitt 2013-02-27 15:17:06 UTC
I tested this again with pygobject 3.7.90 and this works fine now.

Please reopen if you can still reproduce. Thanks!
Comment 7 Nirbheek Chauhan 2013-02-27 15:51:33 UTC
Yep, works now! Thanks. :)