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 697395 - Another round of background leak fixes
Another round of background leak fixes
Status: RESOLVED OBSOLETE
Product: gnome-shell
Classification: Core
Component: background
unspecified
Other All
: Normal normal
: ---
Assigned To: gnome-shell-maint
gnome-shell-maint
3.8.1
Depends on:
Blocks:
 
 
Reported: 2013-04-05 22:10 UTC by Ray Strode [halfline]
Modified: 2021-07-05 14:43 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
background: don't leak background objects during quick changes (3.06 KB, patch)
2013-04-05 22:10 UTC, Ray Strode [halfline]
committed Details | Review
background: when updating image remove old one from cache (2.09 KB, patch)
2013-04-05 22:10 UTC, Ray Strode [halfline]
committed Details | Review
background: stop monitoring file after removing from cache (2.33 KB, patch)
2013-04-05 22:10 UTC, Ray Strode [halfline]
committed Details | Review
backgroundMenu: drop cursor object with rest of menu actors (1.35 KB, patch)
2013-04-05 22:10 UTC, Ray Strode [halfline]
committed Details | Review
popupMenu: fix leak on destroy (2.57 KB, patch)
2013-04-09 00:17 UTC, Ray Strode [halfline]
needs-work Details | Review

Description Ray Strode [halfline] 2013-04-05 22:10:18 UTC
I've hacked up gjs to print whenever an object is created and
whenever it's destroyed.  I've combined that with continuously
running the garbage collector and found a few more leaks.

I'll attach patches for those here.
Comment 1 Ray Strode [halfline] 2013-04-05 22:10:20 UTC
Created attachment 240802 [details] [review]
background: don't leak background objects during quick changes

We currently let some backgrounds "fall through the cracks" if
a bunch of change notifications come in at once.

This commit fixes that.
Comment 2 Ray Strode [halfline] 2013-04-05 22:10:23 UTC
Created attachment 240803 [details] [review]
background: when updating image remove old one from cache

We're removing the new content from the cache instead of the
old content.

This commit fixes that.
Comment 3 Ray Strode [halfline] 2013-04-05 22:10:26 UTC
Created attachment 240804 [details] [review]
background: stop monitoring file after removing from cache
Comment 4 Ray Strode [halfline] 2013-04-05 22:10:29 UTC
Created attachment 240805 [details] [review]
backgroundMenu: drop cursor object with rest of menu actors
Comment 5 Ray Strode [halfline] 2013-04-05 23:12:00 UTC
There's still one problem left:

+ StBoxLayout
+ StBin
+ ShellGenericContainer
+ StBin
+ StDrawingArea
+ ShellGenericContainer
+ ShellGenericContainer
+ StLabel
+ ShellGenericContainer
+ StDrawingArea
+ ShellGenericContainer
+ StLabel

This is the backgroundMenu, so it suggests bug 697119 isn't completely fixed.
Comment 6 drago01 2013-04-06 07:53:28 UTC
Review of attachment 240802 [details] [review]:

OK.
Comment 7 drago01 2013-04-06 07:54:02 UTC
Review of attachment 240803 [details] [review]:

Oh ... good catch.
Comment 8 drago01 2013-04-06 07:54:56 UTC
Review of attachment 240804 [details] [review]:

::: js/ui/background.js
@@ +130,3 @@
+
+        if (filename && this._fileMonitors[filename])
+            delete this._fileMonitors[filename];

Is this enough? i.e does the GC dispose the monitor object?
Comment 9 drago01 2013-04-06 07:55:21 UTC
Review of attachment 240805 [details] [review]:

LG.
Comment 10 Ray Strode [halfline] 2013-04-06 13:43:49 UTC
(In reply to comment #8)
> Review of attachment 240804 [details] [review]:
> 
> ::: js/ui/background.js
> @@ +130,3 @@
> +
> +        if (filename && this._fileMonitors[filename])
> +            delete this._fileMonitors[filename];
> 
> Is this enough? i.e does the GC dispose the monitor object?

Yup. After adding that patch my gjs output started getting

- GInotifyFileMonitor
Comment 11 Ray Strode [halfline] 2013-04-06 13:46:02 UTC
Attachment 240802 [details] pushed as 9eae743 - background: don't leak background objects during quick changes
Attachment 240803 [details] pushed as e98c6ff - background: when updating image remove old one from cache
Attachment 240805 [details] pushed as dc98711 - backgroundMenu: drop cursor object with rest of menu actors
Comment 12 Ray Strode [halfline] 2013-04-06 13:51:51 UTC
Too be more clear about my process, I added to gjs:

+    g_printerr("+ %s\n", g_type_name(priv->gtype));

in associate_js_gobject and

+    g_printerr("- %s\n", g_type_name_from_instance( (GTypeInstance*)
priv->gobj));

in object_instance_finalize. 

Then I started the shell and opened the looking glass console and wrote:

GLib.timeout_add(GLib.PRIORITY_DEFAULT, 500, function() { System.gc(); return
true; })

then opened a shell and typed:

while true; do for f in /usr/share/backgrounds/gnome/*; do gsettings set
org.gnome.desktop.background picture-uri file://$f; sleep 10; done; done

This makes the background change every 10 seconds, but makes the system garbage
collect continuously.  When the the background is changed I see all the new
background objects getting created, and what old background objects get freed.
Comment 13 drago01 2013-04-06 14:01:16 UTC
Review of attachment 240804 [details] [review]:

OK.
Comment 14 Ray Strode [halfline] 2013-04-06 14:46:07 UTC
Attachment 240804 [details] pushed as 0376f22 - background: stop monitoring file after removing from cache
Comment 15 Matthias Clasen 2013-04-07 22:33:03 UTC
all committed here
Comment 16 Ray Strode [halfline] 2013-04-09 00:17:10 UTC
(i left open because of comment 5)
Comment 17 Ray Strode [halfline] 2013-04-09 00:17:30 UTC
Created attachment 240998 [details] [review]
popupMenu: fix leak on destroy

Menus live past destruction because of their delegate
object property.

This commit clears the propery on destroy and breaks the
reference cycle.

Fixes a leak in the background menu when changing backgrounds.
Comment 18 drago01 2013-04-09 12:58:19 UTC
Review of attachment 240998 [details] [review]:

LG.
Comment 19 Jasper St. Pierre (not reading bugmail) 2013-04-09 14:45:24 UTC
Review of attachment 240998 [details] [review]:

Wait a minute. Why isn't the mark and sweep GC taking care of this and disposing the menu?
Comment 20 Ray Strode [halfline] 2013-04-09 20:30:08 UTC
(In reply to comment #19)
> Wait a minute. Why isn't the mark and sweep GC taking care of this and
> disposing the menu?

I'm not completely sure.  What I do know is:

1) this fixes the leak:

+        this.actor.connect('destroy', Lang.bind(this, function() {
+                               this.actor._delegate = null;
+                           }));
+

2) this maintains the leak:
+        this.actor.connect('destroy', Lang.bind(this, function() {
+                               this.actor._otherProperty = this;
+                               this.actor._delegate = null;
+                           }));
+
Comment 21 Jasper St. Pierre (not reading bugmail) 2013-04-09 20:39:03 UTC
We use the _delegate pattern all over the Shell (the DND stuff depends on it, even), so we really need to investigate why the cycle isn't being collected.
Comment 22 Ray Strode [halfline] 2013-04-09 21:38:20 UTC
We also set _delegate to null in most destroy() functions and/or destroy signal handlers.

I'm pretty curious too, though.
Comment 23 drago01 2013-04-09 22:54:49 UTC
(In reply to comment #19)
> Review of attachment 240998 [details] [review]:
> 
> Wait a minute. Why isn't the mark and sweep GC taking care of this and
> disposing the menu?

Hmm... good question.
Comment 24 drago01 2013-04-09 22:57:31 UTC
Review of attachment 240998 [details] [review]:

Jasper is right. This seem to just paper over the real bug.
If we really want it we need a bug file for the GC issue and a comment (unless this turns out to not be a GC bug).
Comment 25 Colin Walters 2013-04-10 17:55:17 UTC
(In reply to comment #24)
> Review of attachment 240998 [details] [review]:
> 
> Jasper is right. This seem to just paper over the real bug.
> If we really want it we need a bug file for the GC issue and a comment (unless
> this turns out to not be a GC bug).

Mozilla has a "cycle collector" for exactly this kind of issue.  GObject toggle references bridge the two worlds of refcounting and GC, but they can't handle what we have here, which is a circular reference *across* the two worlds.

The GObject signal connection forces the function GC-alive, which in turn keeps the "this" object GC-alive.  We have a toggle and we're the last ref, so we don't have a keepalive on "this", but the Spidermonkey GC can't see "through" the gobject world.

So yes, for now we need to avoid keeping references to "this" inside signal callbacks.
Comment 26 Colin Walters 2013-04-11 10:39:48 UTC
(In reply to comment #25)

> The GObject signal connection forces the function GC-alive,

I was wrong about this, Jasper pointed out that that's not true since https://git.gnome.org/browse/gjs/commit/gi/closure.c?id=06aa616a8c9b6d356aefc95a6b0c1c317b86c46a
Comment 27 Bastien Nocera 2014-11-09 23:43:42 UTC
Is this still relevant following the rework of the background code in 3.14?
Comment 28 drago01 2014-11-10 07:31:54 UTC
(In reply to comment #27)
> Is this still relevant following the rework of the background code in 3.14?

The remaining uncommited patch has nothing to do with the background (just the popup menu)
Comment 29 GNOME Infrastructure Team 2021-07-05 14:43:20 UTC
GNOME is going to shut down bugzilla.gnome.org in favor of  gitlab.gnome.org.
As part of that, we are mass-closing older open tickets in bugzilla.gnome.org
which have not seen updates for a longer time (resources are unfortunately
quite limited so not every ticket can get handled).

If you can still reproduce the situation described in this ticket in a recent
and supported software version, then please follow
  https://wiki.gnome.org/GettingInTouch/BugReportingGuidelines
and create a new ticket at
  https://gitlab.gnome.org/GNOME/gnome-shell/-/issues/

Thank you for your understanding and your help.