Which is called first during object destruction?

Quick question. If I have

g_signal_connect_data(
	my_object,
	"some-signal",
	G_CALLBACK(my_signal_listener),
	my_data_1,
	my_destroy_notify_cb,
	G_CONNECT_SWAPPED
);

g_object_weak_ref(my_object, my_weak_notify_cb, my_data_2);

Can I count on the fact that my_weak_notify_cb() will always be called after my_destroy_notify_cb()?

EDIT: I have taken a different approach, so I won’t need an answer anymore. If someone wants to give the solution though it will still help others who might ask the same question in the future.

I would like to give a general reply:

In these situations, there are two approaches:

  1. Test how GLib behaves (printf-testing).
  2. Read the API to see if it’s documented somewhere.

Ideally, if you really want to rely on the current behavior (point 1), and it isn’t documented in the API, then it’s a good practice to contribute to the API documentation and write a unit test for it in GLib :wink:

(this applies to any piece of software a developer relies on, BTW).

It’s actually normally faster to just read the GObject code.

In this case, g_signal_handlers_destroy() is called before quark_weak_refs is cleared, so my_destroy_notify_cb() should be called first.

Note that if this behaviour is not described in the API documentation, it’s not an API guarantee so it may change in future (unlikely though).

Thank you both for your answers.

Yes, the grey area is what made me choose a different approach – which also ended up being more convincing in general.

If this was specified, it still would be a bad idea to depend on it anyway, because closures and weak refs can be removed at any time and so the order may change randomly at runtime anyway if you have code elsewhere that does that.

Yeah you’re right, it’s always better to understand something logically.

The small test program or printf-testing in our codebase can confirm our understanding of the implementation. This reminds me of this paper by Leslie Lamport: The Future of Computing: Logic or Biology

There is also I think a law from somebody that says that whatever you do in a library (or the kernel), some user code will depend and take advantage of implementation details.

So we both agree that it’s always better to rely on the API docs, and not depend on undefined behavior.

This topic was automatically closed 45 days after the last reply. New replies are no longer allowed.