- losses are still possible during applet termination because of missing functionality in GTK3 - related to rhbz#886094
Signed-off-by: Jakub Filak jfilak@redhat.com --- src/applet/applet.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 53 insertions(+), 7 deletions(-)
diff --git a/src/applet/applet.c b/src/applet/applet.c index 7586d11..602e0fa 100644 --- a/src/applet/applet.c +++ b/src/applet/applet.c @@ -528,13 +528,6 @@ static void action_report(NotifyNotification *notification, gchar *action, gpoin
run_event_async(pi, get_autoreport_event_name(), REPORT_UNKNOWN_PROBLEM_IMMEDIATELY); } - - /* Scan dirs and save new $XDG_CACHE_HOME/abrt/applet_dirlist. - * (Oterwise, after a crash, next time applet is started, - * it will show alert icon even if we did click on it - * "in previous life"). We ignore finction return value. - */ - new_dir_exists(/* new dirs list */ NULL); } else problem_info_free(pi); @@ -613,6 +606,13 @@ static void on_notify_close(NotifyNotification *notification, gpointer user_data { VERB3 log("Notify closed!"); g_object_unref(notification); + + /* Scan dirs and save new $XDG_CACHE_HOME/abrt/applet_dirlist. + * (Oterwise, after a crash, next time applet is started, + * it will show alert icon even if we did click on it + * "in previous life"). We ignore finction return value. + */ + new_dir_exists(/* new dirs list */ NULL); }
static NotifyNotification *new_warn_notification(bool persistence) @@ -1088,6 +1088,13 @@ static void Crash(DBusMessage* signal) } }
+ /* + * Can't append dir to the seen list because of directory stealing + * + * append_dirlist(dir); + * + */ + /* If this problem seems to be repeating, do not annoy user with popup dialog. * (The icon in the tray is not suppressed) */ @@ -1324,10 +1331,49 @@ int main(int argc, char** argv)
/* Enter main loop */ gtk_main(); + + /* GTK3 doesn't return from main loop in case of termination due to desktop + * session end. (GTK handles XSMP (X Session Management Protocol) messages + * on its own and exits on session end.) + * + * https://bugs.freedesktop.org/show_bug.cgi?id=32839 + * https://bugzilla.gnome.org/show_bug.cgi?id=639770 + * + * !!! None of the following commands will be executed. !!! + * + * The commands should be pushed into some callback used by deprecated + * gtk_quit_add() or proposed g_flush_all() + * + * Or we can use proposed GtkSMClient (currently available in libegg) + * https://live.gnome.org/SessionManagement/EggSMClient + * + * Or DBus GnomeSession manager (this won't work for other desktops) + * http://people.gnome.org/~mccann/gnome-session/docs/gnome-session.html + */ + #if (GLIB_MAJOR_VERSION == 2 && GLIB_MINOR_VERSION < 31) gdk_threads_leave(); #endif
+ /* new_dir_exists() is called for each notification and if user clicks on + * the abrt icon. Those calls cover 99.97% of detected crashes + * + * The rest of detected crashes: + * + * 0.01% + * applet doesn't append a repeated crash to the seen list if the crash was + * the last caught crash before exit (notification is not shown in case of + * repeated crash) + * + * 0.01% + * applet doesn't append a stolen directory to the seen list if + * notification was closed before the notified directory had been stolen + * + * 0.1% + * crashes of abrt-applet + */ + new_dir_exists(/* new dirs list */ NULL); + if (notify_is_initted()) notify_uninit();
Signed-off-by: Jakub Filak jfilak@redhat.com --- src/applet/applet.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+)
diff --git a/src/applet/applet.c b/src/applet/applet.c index 602e0fa..4408246 100644 --- a/src/applet/applet.c +++ b/src/applet/applet.c @@ -66,6 +66,7 @@ static char *ap_last_problem_dir; static char **s_dirs; static GList *g_deferred_crash_queue; static guint g_deferred_timeout; +static int g_signal_pipe[2];
static bool is_autoreporting_enabled(void) { @@ -1159,6 +1160,35 @@ static void die_if_dbus_error(bool error_flag, DBusError* err, const char* msg) error_msg_and_die("%s", msg); }
+static void handle_signal(int signo) +{ + int save_errno = errno; + + // Enable for debugging only, malloc/printf are unsafe in signal handlers + //VERB3 log("Got signal %d", signo); + + uint8_t sig_caught = signo; + if (write(g_signal_pipe[1], &sig_caught, 1)) + /* we ignore result, if () shuts up stupid compiler */; + + errno = save_errno; +} + +static gboolean handle_sigterm_pipe(GIOChannel *gio, GIOCondition condition, gpointer ptr_unused) +{ + /* It can be only SIGTERM. + * We are going to quit. + * Therefore No read from the channel is necessary. + */ + + /* Next received SIGTERM will kill the applet. */ + signal(SIGTERM, SIG_DFL); + + gtk_main_quit(); + + return FALSE; /* Pointless (loop is done and signal handler was reseted); "please remove this event" */ +} + int main(int argc, char** argv) { /* I18n */ @@ -1329,9 +1359,24 @@ int main(int argc, char** argv)
list_free_with_free(new_dirs);
+ /* Set up signal pipe */ + xpipe(g_signal_pipe); + close_on_exec_on(g_signal_pipe[0]); + close_on_exec_on(g_signal_pipe[1]); + ndelay_on(g_signal_pipe[0]); + ndelay_on(g_signal_pipe[1]); + signal(SIGTERM, handle_signal); + GIOChannel *channel_id_signal = my_io_channel_unix_new(g_signal_pipe[0]); + g_io_add_watch(channel_id_signal, + G_IO_IN | G_IO_PRI | G_IO_ERR | G_IO_HUP | G_IO_NVAL, + handle_sigterm_pipe, + NULL); + /* Enter main loop */ gtk_main();
+ g_io_channel_unref(channel_id_signal); + /* GTK3 doesn't return from main loop in case of termination due to desktop * session end. (GTK handles XSMP (X Session Management Protocol) messages * on its own and exits on session end.)
On 12/17/2012 03:31 PM, Jakub Filak wrote:
Signed-off-by: Jakub Filak jfilak@redhat.com
src/applet/applet.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+)
diff --git a/src/applet/applet.c b/src/applet/applet.c index 602e0fa..4408246 100644 --- a/src/applet/applet.c +++ b/src/applet/applet.c @@ -66,6 +66,7 @@ static char *ap_last_problem_dir; static char **s_dirs; static GList *g_deferred_crash_queue; static guint g_deferred_timeout; +static int g_signal_pipe[2];
static bool is_autoreporting_enabled(void) { @@ -1159,6 +1160,35 @@ static void die_if_dbus_error(bool error_flag, DBusError* err, const char* msg) error_msg_and_die("%s", msg); }
+static void handle_signal(int signo) +{
- int save_errno = errno;
- // Enable for debugging only, malloc/printf are unsafe in signal handlers
- //VERB3 log("Got signal %d", signo);
- uint8_t sig_caught = signo;
- if (write(g_signal_pipe[1], &sig_caught, 1))
/* we ignore result, if () shuts up stupid compiler */;
- errno = save_errno;
+}
+static gboolean handle_sigterm_pipe(GIOChannel *gio, GIOCondition condition, gpointer ptr_unused) +{
- /* It can be only SIGTERM.
* We are going to quit.
* Therefore No read from the channel is necessary.
*/
- /* Next received SIGTERM will kill the applet. */
- signal(SIGTERM, SIG_DFL);
- gtk_main_quit();
- return FALSE; /* Pointless (loop is done and signal handler was reseted); "please remove this event" */
"was reset"
+}
int main(int argc, char** argv) { /* I18n */ @@ -1329,9 +1359,24 @@ int main(int argc, char** argv)
list_free_with_free(new_dirs);
- /* Set up signal pipe */
/* (Comment why do we need to handle SIGTERM. What would happen if we don't?) */
xpipe(g_signal_pipe);
close_on_exec_on(g_signal_pipe[0]);
close_on_exec_on(g_signal_pipe[1]);
ndelay_on(g_signal_pipe[0]);
ndelay_on(g_signal_pipe[1]);
signal(SIGTERM, handle_signal);
GIOChannel *channel_id_signal = my_io_channel_unix_new(g_signal_pipe[0]);
g_io_add_watch(channel_id_signal,
G_IO_IN | G_IO_PRI | G_IO_ERR | G_IO_HUP | G_IO_NVAL,
handle_sigterm_pipe,
NULL);
/* Enter main loop */ gtk_main();
g_io_channel_unref(channel_id_signal);
/* GTK3 doesn't return from main loop in case of termination due to desktop * session end. (GTK handles XSMP (X Session Management Protocol) messages * on its own and exits on session end.)
On 12/17/2012 03:31 PM, Jakub Filak wrote:
- losses are still possible during applet termination because of missing functionality in GTK3
- related to rhbz#886094
Signed-off-by: Jakub Filak jfilak@redhat.com
src/applet/applet.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 53 insertions(+), 7 deletions(-)
diff --git a/src/applet/applet.c b/src/applet/applet.c index 7586d11..602e0fa 100644 --- a/src/applet/applet.c +++ b/src/applet/applet.c @@ -528,13 +528,6 @@ static void action_report(NotifyNotification *notification, gchar *action, gpoin
run_event_async(pi, get_autoreport_event_name(), REPORT_UNKNOWN_PROBLEM_IMMEDIATELY); }
/* Scan dirs and save new $XDG_CACHE_HOME/abrt/applet_dirlist.
* (Oterwise, after a crash, next time applet is started,
* it will show alert icon even if we did click on it
* "in previous life"). We ignore finction return value.
*/
} else problem_info_free(pi);new_dir_exists(/* new dirs list */ NULL);
@@ -613,6 +606,13 @@ static void on_notify_close(NotifyNotification *notification, gpointer user_data { VERB3 log("Notify closed!"); g_object_unref(notification);
- /* Scan dirs and save new $XDG_CACHE_HOME/abrt/applet_dirlist.
* (Oterwise, after a crash, next time applet is started,
* it will show alert icon even if we did click on it
* "in previous life"). We ignore finction return value.
*/
- new_dir_exists(/* new dirs list */ NULL);
}
static NotifyNotification *new_warn_notification(bool persistence) @@ -1088,6 +1088,13 @@ static void Crash(DBusMessage* signal) } }
- /*
* Can't append dir to the seen list because of directory stealing
*
* append_dirlist(dir);
*
*/
- /* If this problem seems to be repeating, do not annoy user with popup dialog. * (The icon in the tray is not suppressed) */
@@ -1324,10 +1331,49 @@ int main(int argc, char** argv)
/* Enter main loop */ gtk_main();
- /* GTK3 doesn't return from main loop in case of termination due to desktop
* session end. (GTK handles XSMP (X Session Management Protocol) messages
* on its own and exits on session end.)
*
* https://bugs.freedesktop.org/show_bug.cgi?id=32839
* https://bugzilla.gnome.org/show_bug.cgi?id=639770
*
* !!! None of the following commands will be executed. !!!
*
* The commands should be pushed into some callback used by deprecated
* gtk_quit_add() or proposed g_flush_all()
*
* Or we can use proposed GtkSMClient (currently available in libegg)
* https://live.gnome.org/SessionManagement/EggSMClient
*
* Or DBus GnomeSession manager (this won't work for other desktops)
* http://people.gnome.org/~mccann/gnome-session/docs/gnome-session.html
*/
#if (GLIB_MAJOR_VERSION == 2 && GLIB_MINOR_VERSION < 31) gdk_threads_leave(); #endif
- /* new_dir_exists() is called for each notification and if user clicks on
* the abrt icon. Those calls cover 99.97% of detected crashes
*
* The rest of detected crashes:
*
* 0.01%
* applet doesn't append a repeated crash to the seen list if the crash was
* the last caught crash before exit (notification is not shown in case of
* repeated crash)
*
* 0.01%
* applet doesn't append a stolen directory to the seen list if
* notification was closed before the notified directory had been stolen
*
* 0.1%
* crashes of abrt-applet
*/
- new_dir_exists(/* new dirs list */ NULL);
- if (notify_is_initted()) notify_uninit();
Looks good to me :)
crash-catcher@lists.fedorahosted.org