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 388321 - gtk_notebook_remove_tab_label
gtk_notebook_remove_tab_label
Status: RESOLVED FIXED
Product: gtk+
Classification: Platform
Component: Widget: GtkNotebook
unspecified
Other All
: Normal major
: Small fix
Assigned To: gtk-bugs
gtk-bugs
: 500049 500415 501870 501929 503625 510433 (view as bug list)
Depends on:
Blocks: 388043
 
 
Reported: 2006-12-21 16:38 UTC by Morten Welinder
Modified: 2008-05-30 18:35 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
Patch to fix life cycle of tab labels (1.91 KB, patch)
2007-11-15 16:02 UTC, Morten Welinder
committed Details | Review
another attempt (1.40 KB, patch)
2007-12-04 18:24 UTC, Matthias Clasen
none Details | Review
fix the fix fixing the fix for the bug (732 bytes, patch)
2007-12-06 12:17 UTC, Christian Persch
committed Details | Review

Description Morten Welinder 2006-12-21 16:38:06 UTC
If something holds a ref to my tab widget, it does not seem to get destroyed.
If the ref is due to a grab, see bug 388043, gtk enters a pretty bad state.

gtk_notebook_remove_tab_label simply unparents.
gtk_notebook_destroy only destroys pages.
Comment 1 Morten Welinder 2007-08-14 01:29:53 UTC
Can we get this on the radar, please?  This feels like a small fix.
Comment 2 Morten Welinder 2007-11-15 16:02:02 UTC
Created attachment 99147 [details] [review]
Patch to fix life cycle of tab labels
Comment 3 Matthias Clasen 2007-11-26 18:25:10 UTC
2007-11-26  Matthias Clasen  <mclasen@redhat.com>

        * gtk/gtknotebook.c (gtk_notebook_update_labels): Short-circuit on
        destroy.
        (gtk_notebook_destroy): Destroy tab_label widgets. (#388321, Morten
        Welinder)
Comment 4 Christian Persch 2007-11-27 22:50:43 UTC
*** Bug 500049 has been marked as a duplicate of this bug. ***
Comment 5 Christian Persch 2007-11-27 22:56:54 UTC
This change broke epiphany: it crashes when closing a window, see bug 500049.

The problem is that epiphany's GtkNotebook's GtkContainer::remove implementation accesses the tab's tab label before calling the parent's ::remove implementation, and with this change, the tab label is already gone at this time.
Comment 6 Morten Welinder 2007-11-28 01:09:25 UTC
Hmm...  Sorry about that.

I am open for other strategies for destroying the labels, but destroyed
they should be.

It seems to me that you are depending on what order children of the notebook
happens to be destroyed.  Any chance you could hold a ref?
Comment 7 Christian Persch 2007-11-29 13:08:25 UTC
*** Bug 500415 has been marked as a duplicate of this bug. ***
Comment 8 Christian Persch 2007-12-04 18:04:11 UTC
I think that prior to calling GtkNotebook's GtkContainer::remove implementation, the tab can be deemed to be in the container, and have its tab label intact; I shouldn't have to do anything like keeping a ref to it myself. The patch broke epiphany; I think it needs to be reverted.

As for a proper fix, why not destroy the tab label in ::remove ?
Comment 9 Matthias Clasen 2007-12-04 18:24:41 UTC
Created attachment 100194 [details] [review]
another attempt
Comment 10 Christian Persch 2007-12-05 18:32:46 UTC
Actually the fix broke evince:

(evince:2447): GLib-GObject-CRITICAL **: g_object_ref: assertion `G_IS_OBJECT (object)' failed

(evince:2447): Gtk-CRITICAL **: gtk_widget_destroy: assertion `GTK_IS_WIDGET (widget)' failed

(evince:2447): GLib-GObject-CRITICAL **: g_object_unref: assertion `G_IS_OBJECT (object)' failed

It appears that |tab_label| is NULL.
Comment 11 Morten Welinder 2007-12-05 20:32:14 UTC
Matthias: notebook->show_tabs = FALSE; is probably useful in any case.
Comment 12 Morten Welinder 2007-12-05 20:50:15 UTC
Christian: more info, please.  Stack trace for first critical, for example.
What did you do at the time?
Comment 13 Christian Persch 2007-12-05 21:34:29 UTC
Step to repro:
0) $ evince some.pdf 
1) Close window

Trace from 1st warning:

  • #0 IA__g_log
    at gmessages.c line 516
  • #1 IA__g_return_if_fail_warning
  • #2 IA__g_object_ref
    at gobject.c line 1719
  • #3 gtk_notebook_remove
    at gtknotebook.c line 4351
  • #4 IA__g_cclosure_marshal_VOID__OBJECT
    at gmarshal.c line 636
  • #5 g_type_class_meta_marshal
    at gclosure.c line 567
  • #6 IA__g_closure_invoke
    at gclosure.c line 490
  • #7 signal_emit_unlocked_R
    at gsignal.c line 2370
  • #8 IA__g_signal_emit_valist
    at gsignal.c line 2199
  • #9 IA__g_signal_emit
    at gsignal.c line 2243
  • #10 gtk_container_remove
    at gtkcontainer.c line 1187
  • #11 gtk_widget_dispose
    at gtkwidget.c line 7842
  • #12 IA__g_object_run_dispose
    at gobject.c line 573
  • #13 gtk_object_destroy
    at gtkobject.c line 403
  • #14 gtk_widget_destroy
    at gtkwidget.c line 2885
  • #15 gtk_notebook_forall
    at gtknotebook.c line 3978
  • #16 gtk_container_foreach
    at gtkcontainer.c line 1480
  • #17 gtk_container_destroy
    at gtkcontainer.c line 1020
  • #18 gtk_notebook_destroy
    at gtknotebook.c line 1473
  • #19 IA__g_cclosure_marshal_VOID__VOID
    at gmarshal.c line 77
  • #20 g_type_class_meta_marshal
    at gclosure.c line 567
  • #21 IA__g_closure_invoke
    at gclosure.c line 490
  • #22 signal_emit_unlocked_R
    at gsignal.c line 2556
  • #23 IA__g_signal_emit_valist
    at gsignal.c line 2199
  • #24 IA__g_signal_emit
    at gsignal.c line 2243
  • #25 gtk_object_dispose
    at gtkobject.c line 418
  • #26 gtk_widget_dispose
    at gtkwidget.c line 7850
  • #27 IA__g_object_run_dispose
    at gobject.c line 573
  • #28 gtk_object_destroy
    at gtkobject.c line 403
  • #29 gtk_widget_destroy
    at gtkwidget.c line 2885
  • #30 gtk_box_forall
    at gtkbox.c line 799
  • #31 gtk_container_foreach
    at gtkcontainer.c line 1480
  • #32 gtk_container_destroy
    at gtkcontainer.c line 1020
  • #33 IA__g_cclosure_marshal_VOID__VOID
    at gmarshal.c line 77
  • #34 g_type_class_meta_marshal
    at gclosure.c line 567
  • #35 IA__g_closure_invoke
    at gclosure.c line 490
  • #36 signal_emit_unlocked_R
    at gsignal.c line 2556
  • #37 IA__g_signal_emit_valist
    at gsignal.c line 2199
  • #38 IA__g_signal_emit
    at gsignal.c line 2243
  • #39 gtk_object_dispose
    at gtkobject.c line 418
  • #40 gtk_widget_dispose
    at gtkwidget.c line 7850


That means that in this code:

+  tab_label = page->tab_label;
+  g_object_ref (tab_label);
   gtk_notebook_remove_tab_label (notebook, page);
+  if (destroying)
+    gtk_widget_destroy (tab_label);
+  g_object_unref (tab_label);

the tab_label is NULL.
Comment 14 Morten Welinder 2007-12-05 21:42:40 UTC
Try the obvious ifs:

+  tab_label = page->tab_label;
+  if (tab_label)
+     g_object_ref (tab_label);
   gtk_notebook_remove_tab_label (notebook, page);
+  if (tab_label)
+    {
+      if (destroying)
+        gtk_widget_destroy (tab_label);
+      g_object_unref (tab_label);
+    }
Comment 15 Cosimo Cecchi 2007-12-06 00:20:38 UTC
*** Bug 501929 has been marked as a duplicate of this bug. ***
Comment 16 Cosimo Cecchi 2007-12-06 00:22:57 UTC
*** Bug 501870 has been marked as a duplicate of this bug. ***
Comment 17 Christian Persch 2007-12-06 12:17:40 UTC
Created attachment 100378 [details] [review]
fix the fix fixing the fix for the bug

This fixes the problem in evince.
Comment 18 Matthias Clasen 2007-12-10 06:24:46 UTC
2007-12-10  Matthias Clasen  <mclasen@redhat.com>

        * gtk/gtknotebook.c (gtk_notebook_real_remove): Another fix
        to avoid further fallout from the fix for bug 388321.

Comment 19 Xan Lopez 2007-12-16 12:37:17 UTC
*** Bug 503625 has been marked as a duplicate of this bug. ***
Comment 20 Christian Persch 2008-05-30 18:35:36 UTC
*** Bug 510433 has been marked as a duplicate of this bug. ***