Comment 7 for bug 441190

Revision history for this message
James Westby (james-w) wrote :

It looks to me as though dbus-glib isn't taking part in dbus' reference counting:

In dbus, as things are being torn down:

  _dbus_watch_unref(...
  .
  .
  .
    if (watch->refcount == 0)
      {
        dbus_watch_set_data (watch, NULL, NULL); /* call free_data_function */

which frees the data.

in dbus-glib

  connection_setup_add_watch(...
  .
  .
  .
    channel = g_io_channel_unix_new (dbus_watch_get_unix_fd (watch));

    handler->source = g_io_create_watch (channel, condition);
    g_source_set_callback (handler->source, (GSourceFunc) io_handler_dispatch, handler,
                           io_handler_source_finalized);

so io_handler_source_finalized will be called as the watch is torn down

  io_handler_source_finalized (gpointer data)
  {
    IOHandler *handler;

    handler = data;

    if (handler->watch)
      dbus_watch_set_data (handler->watch, NULL, NULL);

which frees the data regardless.

I think this isn't an issue for every use, as we are in an exception case in
dbus itself:

    if (_dbus_message_loader_get_is_corrupted (transport->loader))
    {
      _dbus_verbose ("Corrupted message stream, disconnecting\n");
      _dbus_transport_disconnect (transport);

As for a fix, I'm not sure, should dbus-glib take part in the refcounting,
or just not bother freeing the data and rely on dbus to do it?

Thanks,

James