From f90fce80371ac12d97c6adc65a9437e4a3a7b268 Mon Sep 17 00:00:00 2001
From: Kevin Smith <git@kismith.co.uk>
Date: Wed, 14 Mar 2012 13:12:24 +0000
Subject: Dispose of notification callbacks once the account signs out.

Fixes segfaults caused by clicking notifications after
the handlers had been freed.

Does not fix GrowlNotifier, which needs fixing later.

diff --git a/SwifTools/Notifier/GrowlNotifier.h b/SwifTools/Notifier/GrowlNotifier.h
index f4e6803..f1fb8c6 100644
--- a/SwifTools/Notifier/GrowlNotifier.h
+++ b/SwifTools/Notifier/GrowlNotifier.h
@@ -29,6 +29,9 @@ namespace Swift {
 			void handleNotificationClicked(void* data);
 			void handleNotificationTimedOut(void* data);
 		
+			virtual void purgeCallbacks() {
+#warning FIXME: Implement
+			}
 		private:
 			class Private;
 			boost::shared_ptr<Private> p;
diff --git a/SwifTools/Notifier/LoggingNotifier.h b/SwifTools/Notifier/LoggingNotifier.h
index 32e0610..3d62593 100644
--- a/SwifTools/Notifier/LoggingNotifier.h
+++ b/SwifTools/Notifier/LoggingNotifier.h
@@ -25,6 +25,8 @@ namespace Swift {
 					boost::function<void()> callback;
 			};
 
+			virtual void purgeCallbacks() {}
+
 			std::vector<Notification> notifications;
 	};
 }
diff --git a/SwifTools/Notifier/Notifier.h b/SwifTools/Notifier/Notifier.h
index 1bcd58d..9537ec1 100644
--- a/SwifTools/Notifier/Notifier.h
+++ b/SwifTools/Notifier/Notifier.h
@@ -36,6 +36,9 @@ namespace Swift {
 				return false;
 			}
 
+			/** Remove any pending callbacks. */
+			virtual void purgeCallbacks() = 0;
+
 		protected:
 			std::string typeToString(Type type);
 			static std::vector<Type> getAllTypes();
diff --git a/SwifTools/Notifier/NullNotifier.h b/SwifTools/Notifier/NullNotifier.h
index 2fa9c11..576dd85 100644
--- a/SwifTools/Notifier/NullNotifier.h
+++ b/SwifTools/Notifier/NullNotifier.h
@@ -13,5 +13,6 @@ namespace Swift {
 		public:
 			virtual void showMessage(Type, const std::string&, const std::string&, const boost::filesystem::path&, boost::function<void()>) {
 			}
+			virtual void purgeCallbacks() {
 	};
 }
diff --git a/SwifTools/Notifier/SnarlNotifier.h b/SwifTools/Notifier/SnarlNotifier.h
index c96dfa6..eb0eb5a 100644
--- a/SwifTools/Notifier/SnarlNotifier.h
+++ b/SwifTools/Notifier/SnarlNotifier.h
@@ -22,6 +22,10 @@ namespace Swift {
 			virtual void showMessage(Type type, const std::string& subject, const std::string& description, const boost::filesystem::path& picture, boost::function<void()> callback);
 			virtual bool isAvailable() const;
 		
+			virtual void purgeCallbacks() {
+				notifications.clear();
+			}
+
 		private:
 			void handleMessageReceived(MSG* message);
 
diff --git a/SwifTools/Notifier/TogglableNotifier.h b/SwifTools/Notifier/TogglableNotifier.h
index 7abfd42..a4f0bb6 100644
--- a/SwifTools/Notifier/TogglableNotifier.h
+++ b/SwifTools/Notifier/TogglableNotifier.h
@@ -50,6 +50,10 @@ namespace Swift {
 				return notifier->isExternallyConfigured();
 			}
 
+			virtual void purgeCallbacks() {
+				notifier->purgeCallbacks();
+			}
+
 		private:
 			Notifier* notifier;
 			bool persistentEnabled;
diff --git a/Swift/Controllers/EventNotifier.cpp b/Swift/Controllers/EventNotifier.cpp
index 7ecc27c..e643ab3 100644
--- a/Swift/Controllers/EventNotifier.cpp
+++ b/Swift/Controllers/EventNotifier.cpp
@@ -27,6 +27,7 @@ EventNotifier::EventNotifier(EventController* eventController, Notifier* notifie
 }
 
 EventNotifier::~EventNotifier() {
+	notifier->purgeCallbacks();
 	eventController->onEventQueueEventAdded.disconnect(boost::bind(&EventNotifier::handleEventAdded, this, _1));
 }
 
diff --git a/Swift/QtUI/WindowsNotifier.cpp b/Swift/QtUI/WindowsNotifier.cpp
index 1789451..212f0ca 100644
--- a/Swift/QtUI/WindowsNotifier.cpp
+++ b/Swift/QtUI/WindowsNotifier.cpp
@@ -47,4 +47,8 @@ void WindowsNotifier::handleMessageClicked() {
 	}
 }
 
+void WindowsNotifier::purgeCallbacks() {
+	lastCallback = boost::function<void()>();
+}
+
 }
diff --git a/Swift/QtUI/WindowsNotifier.h b/Swift/QtUI/WindowsNotifier.h
index 062b76f..b2b5577 100644
--- a/Swift/QtUI/WindowsNotifier.h
+++ b/Swift/QtUI/WindowsNotifier.h
@@ -23,7 +23,8 @@ namespace Swift {
 			~WindowsNotifier();
 
 			virtual void showMessage(Type type, const std::string& subject, const std::string& description, const boost::filesystem::path& picture, boost::function<void()> callback);
-		
+			virtual void purgeCallbacks();
+
 		private slots:
 			void handleMessageClicked();
 
-- 
cgit v0.10.2-6-g49f6