Request for approval



Hi

This is a request for approval for a couple Evolution crashes.

Bug is http://bugzilla.ximian.com/show_bug.cgi?id=72835

It's already been approved by the Evolution team
-- 
Rodrigo Moya <rodrigo novell com>
--- Begin Message ---
On Thu, 2005-03-03 at 20:18 +0100, Rodrigo Moya wrote:
> On Thu, 2005-03-03 at 19:56 +0100, Rodrigo Moya wrote:
> > On Mon, 2005-02-28 at 13:16 +0100, Rodrigo Moya wrote:
> > > This removes use of g_assert and does a better management of the
> > > midnight_refresh
> > 
> > discard this one, this fix is now included in the attached patch, which
> > also fixes #72835 (crash in alarm daemon)
> 
> sorry, previous patch didn't fix all cases mentioned in the bug. Now
> this new one should fix all of them.

a new version, with a missing line in
alarm-notify-dialog.c#dialog_response_cb to call the callback also when
'Close' is selected. This was preventing the dialog to be closed.
-- 
Rodrigo Moya <rodrigo novell com>
Index: ChangeLog
===================================================================
RCS file: /cvs/gnome/evolution/calendar/ChangeLog,v
retrieving revision 1.2680
diff -u -p -r1.2680 ChangeLog
--- ChangeLog	1 Mar 2005 01:14:56 -0000	1.2680
+++ ChangeLog	4 Mar 2005 11:24:38 -0000
@@ -1,3 +1,21 @@
+2005-xx-xx  Rodrigo Moya <rodrigo novell com>
+
+	Fixes #72835
+
+	* gui/alarm-notify/alarm-notify-dialog.[ch] (alarm_notify_dialog):
+	changed to return the dialog we create, and to run in the background.
+	(dialog_response_cb): response callback for the dialog.
+
+	* gui/alarm-notify/alarm-queue.c (alarm_queue_done): don't g_assert,
+	just check for midnight_refresh pointer, and clear it up if not NULL.
+	Also, traverse all clients with g_hash_table_foreach_remove.
+	(free_client_alarms_cb, alarm_queue_remove_client, load_alarms): added
+	missing cleanup code.
+	(queue_midnight_refresh): don't g_assert, just check for midnigh_refresh
+	pointer and clear it up if not NULL.
+	(open_alarm_dialog): store the dialog returned by alarm_notify_dialog().
+	(tray_icon_destroyed_cb): destroy the dialog if still around.
+
 2005-02-28  Harish Krishnaswamy  <kharish novell com>
 
         Fixes #69556
Index: gui/alarm-notify/alarm-notify-dialog.c
===================================================================
RCS file: /cvs/gnome/evolution/calendar/gui/alarm-notify/alarm-notify-dialog.c,v
retrieving revision 1.32
diff -u -p -r1.32 alarm-notify-dialog.c
--- gui/alarm-notify/alarm-notify-dialog.c	17 Dec 2004 18:03:22 -0000	1.32
+++ gui/alarm-notify/alarm-notify-dialog.c	4 Mar 2005 11:24:38 -0000
@@ -81,6 +81,36 @@ an_update_minutes_label (GtkSpinButton *
 	g_free (new_label);
 }
 
+static void
+dialog_response_cb (GtkDialog *dialog, guint response_id, gpointer user_data)
+{
+	int snooze_timeout;
+	AlarmNotify *an = user_data;
+
+	switch (response_id) {
+	case AN_RESPONSE_EDIT:
+		(* an->func) (ALARM_NOTIFY_EDIT, -1, an->func_data);
+		break;
+	case AN_RESPONSE_SNOOZE:
+		snooze_timeout = gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (an->snooze_time));
+		(* an->func) (ALARM_NOTIFY_SNOOZE, snooze_timeout, an->func_data);
+		break;
+	case GTK_RESPONSE_CLOSE:
+	case GTK_RESPONSE_DELETE_EVENT:
+		(* an->func) (ALARM_NOTIFY_CLOSE, -1, an->func_data);
+		break;
+	}
+}
+
+static void
+dialog_destroyed_cb (GtkWidget *dialog, gpointer user_data)
+{
+	AlarmNotify *an = user_data;
+
+	g_object_unref (an->xml);
+	g_free (an);
+}
+
 /**
  * alarm_notify_dialog:
  * @trigger: Trigger time for the alarm.
@@ -96,9 +126,9 @@ an_update_minutes_label (GtkSpinButton *
  * Runs the alarm notification dialog.  The specified @func will be used to
  * notify the client about result of the actions in the dialog.
  *
- * Return value: a pointer to the dialog structure if successful or NULL if an error occurs.
+ * Return value: a pointer to the dialog widget created or NULL if there is an error.
  **/
-void
+GtkWidget *
 alarm_notify_dialog (time_t trigger, time_t occur_start, time_t occur_end,
 		     ECalComponentVType vtype, const char *summary,
 		     const char *description, const char *location,
@@ -111,17 +141,15 @@ alarm_notify_dialog (time_t trigger, tim
 	char *start, *end;
 	char *icon_path;
 	GList *icon_list;
-	int snooze_timeout;
 
-	g_return_if_fail (trigger != -1);
+	g_return_val_if_fail (trigger != -1, NULL);
 
 	/* Only VEVENTs or VTODOs can have alarms */
-	g_return_if_fail (vtype == E_CAL_COMPONENT_EVENT
-			  || vtype == E_CAL_COMPONENT_TODO);
-	g_return_if_fail (summary != NULL);
-	g_return_if_fail (description != NULL);
-	g_return_if_fail (location != NULL);
-	g_return_if_fail (func != NULL);
+	g_return_val_if_fail (vtype == E_CAL_COMPONENT_EVENT || vtype == E_CAL_COMPONENT_TODO, NULL);
+	g_return_val_if_fail (summary != NULL, NULL);
+	g_return_val_if_fail (description != NULL, NULL);
+	g_return_val_if_fail (location != NULL, NULL);
+	g_return_val_if_fail (func != NULL, NULL);
 
 	an = g_new0 (AlarmNotify, 1);
 
@@ -132,7 +160,7 @@ alarm_notify_dialog (time_t trigger, tim
 	if (!an->xml) {
 		g_message ("alarm_notify_dialog(): Could not load the Glade XML file!");
 		g_free (an);
-		return;
+		return NULL;
 	}
 
 	an->dialog = glade_xml_get_widget (an->xml, "alarm-notify");
@@ -149,7 +177,7 @@ alarm_notify_dialog (time_t trigger, tim
 		g_message ("alarm_notify_dialog(): Could not find all widgets in Glade file!");
 		g_object_unref (an->xml);
 		g_free (an);
-		return;
+		return NULL;
 	}
 
 	gtk_widget_realize (an->dialog);
@@ -199,20 +227,9 @@ alarm_notify_dialog (time_t trigger, tim
 		g_list_free (icon_list);
 	}
 
-	switch (gtk_dialog_run (GTK_DIALOG (an->dialog))) {
-	case AN_RESPONSE_EDIT:
-	  (* an->func) (ALARM_NOTIFY_EDIT, -1, an->func_data);
-	  break;
-	case AN_RESPONSE_SNOOZE:
-	  snooze_timeout = gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (an->snooze_time));
-	  (* an->func) (ALARM_NOTIFY_SNOOZE, snooze_timeout, an->func_data);
-	  break;
-	case GTK_RESPONSE_CLOSE:
-	case GTK_RESPONSE_DELETE_EVENT:
-	  break;
-	}
-	gtk_widget_destroy (an->dialog);
-	
-	g_object_unref (an->xml);
-	g_free (an);
+	g_signal_connect (G_OBJECT (an->dialog), "response", G_CALLBACK (dialog_response_cb), an);
+	g_signal_connect (G_OBJECT (an->dialog), "destroy", G_CALLBACK (dialog_destroyed_cb), an);
+	gtk_widget_show (an->dialog);
+
+	return an->dialog;
 }
Index: gui/alarm-notify/alarm-notify-dialog.h
===================================================================
RCS file: /cvs/gnome/evolution/calendar/gui/alarm-notify/alarm-notify-dialog.h,v
retrieving revision 1.11
diff -u -p -r1.11 alarm-notify-dialog.h
--- gui/alarm-notify/alarm-notify-dialog.h	23 Nov 2004 06:24:57 -0000	1.11
+++ gui/alarm-notify/alarm-notify-dialog.h	4 Mar 2005 11:24:38 -0000
@@ -24,6 +24,7 @@
 #include <time.h>
 #include <glib.h>
 #include <libecal/e-cal-component.h>
+#include <gtk/gtkwidget.h>
 
 
 
@@ -35,10 +36,10 @@ typedef enum {
 
 typedef void (* AlarmNotifyFunc) (AlarmNotifyResult result, int snooze_mins, gpointer data);
 
-void alarm_notify_dialog (time_t trigger, time_t occur_start, time_t occur_end,
-			  ECalComponentVType vtype, const char *summary,
-			  const char *description, const char *location,
-			  AlarmNotifyFunc func, gpointer func_data);
+GtkWidget *alarm_notify_dialog (time_t trigger, time_t occur_start, time_t occur_end,
+				ECalComponentVType vtype, const char *summary,
+				const char *description, const char *location,
+				AlarmNotifyFunc func, gpointer func_data);
 
 
 #endif
Index: gui/alarm-notify/alarm-queue.c
===================================================================
RCS file: /cvs/gnome/evolution/calendar/gui/alarm-notify/alarm-queue.c,v
retrieving revision 1.79
diff -u -p -r1.79 alarm-queue.c
--- gui/alarm-notify/alarm-queue.c	22 Dec 2004 07:37:25 -0000	1.79
+++ gui/alarm-notify/alarm-queue.c	4 Mar 2005 11:24:38 -0000
@@ -147,7 +147,10 @@ queue_midnight_refresh (void)
 	time_t midnight;
 	icaltimezone *zone;
 
-	g_assert (midnight_refresh_id == NULL);
+	if (midnight_refresh_id != NULL) {
+		alarm_remove (midnight_refresh_id);
+		midnight_refresh_id = NULL;
+	}
 
 	zone = config_data_get_timezone ();
 
@@ -180,7 +183,11 @@ midnight_refresh_cb (gpointer alarm_id, 
 
 	/* Re-schedule the midnight update */
 
-	midnight_refresh_id = NULL;
+	if (midnight_refresh_id != NULL) {
+		alarm_remove (midnight_refresh_id);
+		midnight_refresh_id = NULL;
+	}
+
 	queue_midnight_refresh ();
 }
 
@@ -408,6 +415,7 @@ load_alarms (ClientAlarms *ca, time_t st
 
 	/* create the live query */
 	if (ca->query) {
+		g_signal_handlers_disconnect_matched (ca->query, G_SIGNAL_MATCH_DATA, 0, 0, NULL, NULL, ca);
 		g_object_unref (ca->query);
 		ca->query = NULL;
 	}
@@ -781,6 +789,11 @@ tray_icon_destroyed_cb (GtkWidget *tray,
 	if (tray_data->cqa != NULL)
 		remove_queued_alarm (tray_data->cqa, tray_data->alarm_id, TRUE, TRUE);
 
+	if (tray_data->alarm_dialog != NULL) {
+		gtk_widget_destroy (tray_data->alarm_dialog);
+		tray_data->alarm_dialog = NULL;
+	}
+
 	if (tray_data->summary != NULL) {
 		g_free (tray_data->summary);
 		tray_data->summary = NULL;
@@ -818,14 +831,14 @@ open_alarm_dialog (TrayIconData *tray_da
 	qa = lookup_queued_alarm (tray_data->cqa, tray_data->alarm_id);
 	if (qa) {
 		gtk_widget_hide (tray_data->tray_icon);
-		alarm_notify_dialog (tray_data->trigger,
-				     qa->instance->occur_start,
-				     qa->instance->occur_end,
-				     e_cal_component_get_vtype (tray_data->comp),
-				     tray_data->summary,
-				     tray_data->description,
-				     tray_data->location,
-				     notify_dialog_cb, tray_data);
+		tray_data->alarm_dialog = alarm_notify_dialog (tray_data->trigger,
+							       qa->instance->occur_start,
+							       qa->instance->occur_end,
+							       e_cal_component_get_vtype (tray_data->comp),
+							       tray_data->summary,
+							       tray_data->description,
+							       tray_data->location,
+							       notify_dialog_cb, tray_data);
 	}
 
 	return TRUE;
@@ -1227,15 +1240,32 @@ alarm_queue_init (void)
 	alarm_queue_inited = TRUE;
 }
 
-static void
+static gboolean
 free_client_alarms_cb (gpointer key, gpointer value, gpointer user_data)
 {
 	ClientAlarms *ca = value;
 
 	if (ca) {
-		g_object_unref (ca->client);
+		remove_client_alarms (ca);
+		if (ca->client) {
+			g_signal_handlers_disconnect_matched (ca->client, G_SIGNAL_MATCH_DATA,
+							      0, 0, NULL, NULL, ca);
+			g_object_unref (ca->client);
+		}
+
+		if (ca->query) {
+			g_signal_handlers_disconnect_matched (ca->query, G_SIGNAL_MATCH_DATA,
+							      0, 0, NULL, NULL, ca);
+			g_object_unref (ca->query);
+		}
+
+		g_hash_table_destroy (ca->uid_alarms_hash);
+
 		g_free (ca);
+		return TRUE;
 	}
+
+	return FALSE;
 }
 
 /**
@@ -1253,13 +1283,14 @@ alarm_queue_done (void)
 	/* All clients must be unregistered by now */
 	g_return_if_fail (g_hash_table_size (client_alarms_hash) == 0);
 
-	g_hash_table_foreach (client_alarms_hash, (GHFunc) free_client_alarms_cb, NULL);
+	g_hash_table_foreach_remove (client_alarms_hash, (GHRFunc) free_client_alarms_cb, NULL);
 	g_hash_table_destroy (client_alarms_hash);
 	client_alarms_hash = NULL;
 
-	g_assert (midnight_refresh_id != NULL);
-	alarm_remove (midnight_refresh_id);
-	midnight_refresh_id = NULL;
+	if (midnight_refresh_id != NULL) {
+		alarm_remove (midnight_refresh_id);
+		midnight_refresh_id = NULL;
+	}
 
 	alarm_queue_inited = FALSE;
 }
@@ -1373,13 +1404,19 @@ alarm_queue_remove_client (ECal *client)
 
 	/* Clean up */
 
-	g_signal_handlers_disconnect_matched (ca->client, G_SIGNAL_MATCH_DATA,
-					      0, 0, NULL, NULL, ca);
+	if (ca->client) {
+		g_signal_handlers_disconnect_matched (ca->client, G_SIGNAL_MATCH_DATA,
+						      0, 0, NULL, NULL, ca);
+		g_object_unref (ca->client);
+		ca->client = NULL;
+	}
 
-	g_object_unref (ca->query);
-	ca->query = NULL;
-	g_object_unref (ca->client);
-	ca->client = NULL;
+	if (ca->query) {
+		g_signal_handlers_disconnect_matched (ca->query, G_SIGNAL_MATCH_DATA,
+						      0, 0, NULL, NULL, ca);
+		g_object_unref (ca->query);
+		ca->query = NULL;
+	}
 
 	g_hash_table_destroy (ca->uid_alarms_hash);
 	ca->uid_alarms_hash = NULL;

--- End Message ---


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