[f-spot/stable-0.6] Don't segfault on shutdown in ImageLoaderThread.
- From: Ruben Vermeersch <rubenv src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [f-spot/stable-0.6] Don't segfault on shutdown in ImageLoaderThread.
- Date: Tue, 22 Jun 2010 20:50:12 +0000 (UTC)
commit a0de2ac6269d43a73940be0a69dc137985f060d4
Author: Ruben Vermeersch <ruben savanne be>
Date: Tue Jun 22 22:48:34 2010 +0200
Don't segfault on shutdown in ImageLoaderThread.
Backported fix for https://bugzilla.gnome.org/show_bug.cgi?id=621597
Requested here: https://bugzilla.gnome.org/show_bug.cgi?id=621823
src/Core/App.cs | 2 +-
src/ImageLoaderThread.cs | 45 ++++++++++++++++++++++++++++++++-------------
2 files changed, 33 insertions(+), 14 deletions(-)
---
diff --git a/src/Core/App.cs b/src/Core/App.cs
index c2207df..d0a26a9 100644
--- a/src/Core/App.cs
+++ b/src/Core/App.cs
@@ -340,7 +340,7 @@ namespace FSpot
Log.Information ("Exiting...");
Banshee.Kernel.Scheduler.Dispose ();
Database.Dispose ();
- ImageLoaderThread.Cleanup ();
+ ImageLoaderThread.CleanAll ();
Gtk.Application.Quit ();
System.Environment.Exit (0);
}
diff --git a/src/ImageLoaderThread.cs b/src/ImageLoaderThread.cs
index 148c7da..cc340cf 100644
--- a/src/ImageLoaderThread.cs
+++ b/src/ImageLoaderThread.cs
@@ -46,10 +46,10 @@ public class ImageLoaderThread {
// Private members.
+ static List<ImageLoaderThread> instances = new List<ImageLoaderThread> ();
/* The thread used to handle the requests. */
private Thread worker_thread;
- private static ArrayList all_worker_threads = new ArrayList ();
/* The request queue; it's shared between the threads so it
needs to be locked prior to access. */
@@ -76,6 +76,7 @@ public class ImageLoaderThread {
already or not. */
private bool pending_notify_notified;
+ volatile bool should_cancel = false;
// Public API.
@@ -91,10 +92,17 @@ public class ImageLoaderThread {
pending_notify = new ThreadNotify (new Gtk.ReadyEvent (HandleProcessedRequests));
+ instances.Add (this);
+ }
+
+ void StartWorker ()
+ {
+ if (worker_thread != null)
+ return;
+
+ should_cancel = false;
worker_thread = new Thread (new ThreadStart (WorkerThread));
worker_thread.Start ();
-
- all_worker_threads.Add (worker_thread);
}
int block_count;
@@ -112,17 +120,23 @@ public class ImageLoaderThread {
}
}
- // FIXME?
- static public void Cleanup ()
+ public void Cleanup ()
{
- foreach (Thread t in all_worker_threads)
- t.Abort ();
+ should_cancel = true;
+ if (worker_thread != null) {
+ lock (queue) {
+ Monitor.Pulse (queue);
+ }
+ worker_thread.Join ();
+ }
+ worker_thread = null;
}
- public void Request (Uri uri, int order)
- {
- Request (uri, order, 0, 0);
- }
+ public static void CleanAll ()
+ {
+ foreach (var thread in instances)
+ thread.Cleanup ();
+ }
public virtual void Request (Uri uri, int order, int width, int height)
{
@@ -172,6 +186,8 @@ public class ImageLoaderThread {
private bool InsertRequest (Uri uri, int order, int width, int height)
{
+ StartWorker ();
+
/* Check if this is the same as the request currently being processed. */
lock(processed_requests) {
if (current_request != null && current_request.uri == uri)
@@ -205,7 +221,7 @@ public class ImageLoaderThread {
private void WorkerThread ()
{
try {
- while (true) {
+ while (!should_cancel) {
lock (processed_requests) {
if (current_request != null) {
processed_requests.Enqueue (current_request);
@@ -221,8 +237,11 @@ public class ImageLoaderThread {
lock (queue) {
- while (queue.Count == 0 || block_count > 0)
+ while ((queue.Count == 0 || block_count > 0) && !should_cancel)
Monitor.Wait (queue);
+
+ if (should_cancel)
+ return;
int pos = queue.Count - 1;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]