[gnome-shell] screenshot: Ensure that ShellScreenshot stays alive until the callback



commit 2b87bb015cd057ea44f8d9767386f6437848ed71
Author: Jasper St. Pierre <jstpierre mecheye net>
Date:   Sun Mar 25 11:54:08 2012 -0300

    screenshot: Ensure that ShellScreenshot stays alive until the callback
    
    We've been dangling on the edge of unsafety, unnoticed, for a little while
    about the reference count safety of ShellScreenshot. GJS owns the entire
    reference count, so as soon as it goes out of scope it could die, causing
    GJS to try and fetch the corresponding wrapper object for a stale pointer.
    We haven't seen any crashes because of luck -- SpiderMonkey tries to group
    together deallocations to limit GC pauses, and there isn't really a lot
    of GC pressure in the duration that a screenshot happens, so we tend to
    be mostly stable. But in the case that you create a lot of objects while
    a screenshot is going on, by hammering the "Print Screen" button, for
    example, you can destroy the GObject before the callback finishes.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=672775

 src/shell-screenshot.c |    7 ++++---
 1 files changed, 4 insertions(+), 3 deletions(-)
---
diff --git a/src/shell-screenshot.c b/src/shell-screenshot.c
index b0dcfa3..33b981e 100644
--- a/src/shell-screenshot.c
+++ b/src/shell-screenshot.c
@@ -65,6 +65,7 @@ on_screenshot_written (GObject *source,
                                &screenshot_data->screenshot_area);
 
   cairo_surface_destroy (screenshot_data->image);
+  g_object_unref (screenshot_data->screenshot);
   g_free (screenshot_data->filename);
   g_free (screenshot_data);
 }
@@ -262,7 +263,7 @@ shell_screenshot_screenshot (ShellScreenshot *screenshot,
   ClutterActor *stage;
   _screenshot_data *data = g_new0 (_screenshot_data, 1);
 
-  data->screenshot = screenshot;
+  data->screenshot = g_object_ref (screenshot);
   data->filename = g_strdup (filename);
   data->callback = callback;
   data->include_cursor = include_cursor;
@@ -301,7 +302,7 @@ shell_screenshot_screenshot_area (ShellScreenshot *screenshot,
   ClutterActor *stage;
   _screenshot_data *data = g_new0 (_screenshot_data, 1);
 
-  data->screenshot = screenshot;
+  data->screenshot = g_object_ref (screenshot);
   data->filename = g_strdup (filename);
   data->screenshot_area.x = x;
   data->screenshot_area.y = y;
@@ -350,7 +351,7 @@ shell_screenshot_screenshot_window (ShellScreenshot *screenshot,
   MetaRectangle rect;
   cairo_rectangle_int_t clip;
 
-  screenshot_data->screenshot = screenshot;
+  screenshot_data->screenshot = g_object_ref (screenshot);
   screenshot_data->filename = g_strdup (filename);
   screenshot_data->callback = callback;
 



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]