From 12ba2b222f4c23be39542443e93dff45405f1b70 Mon Sep 17 00:00:00 2001 From: Giovanni Campagna <gcampagna@src.gnome.org> Date: Wed, 28 Nov 2012 19:45:52 +0100 Subject: [PATCH] Add a way to get backtraces from criticals and warnings Attaching gdb and running with G_DEBUG=fatal-warnings is not a very fast to debug a specific issue (especially if you have warnings at startup, since then you need to run the shell from a terminal). Instead, introduce a new SHELL_DEBUG environment variable that can be set to backtrace-warning, causing a gjs_dumpstack() after every warning or critical. https://bugzilla.gnome.org/show_bug.cgi?id=700262 --- src/main.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/src/main.c b/src/main.c index ca2116a96..25d708d6d 100644 --- a/src/main.c +++ b/src/main.c @@ -47,6 +47,11 @@ static char *session_mode = NULL; #define DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER 1 #define DBUS_REQUEST_NAME_REPLY_ALREADY_OWNER 4 +enum { + SHELL_DEBUG_BACKTRACE_WARNINGS = 1, +}; +static int _shell_debug; + static void shell_dbus_acquire_name (GDBusProxy *bus, guint32 request_name_flags, @@ -269,6 +274,17 @@ shell_a11y_init (void) } } +static void +shell_init_debug (const char *debug_env) +{ + static const GDebugKey keys[] = { + { "backtrace-warnings", SHELL_DEBUG_BACKTRACE_WARNINGS } + }; + + _shell_debug = g_parse_debug_string (debug_env, keys, + G_N_ELEMENTS (keys)); +} + static void default_log_handler (const char *log_domain, GLogLevelFlags log_level, @@ -286,6 +302,15 @@ default_log_handler (const char *log_domain, * with those. */ if (!log_domain || !g_str_has_prefix (log_domain, "tp-glib")) g_log_default_handler (log_domain, log_level, message, data); + + /* Filter out Gjs logs, those already have the stack */ + if (log_domain && strcmp (log_domain, "Gjs") == 0) + return; + + if ((_shell_debug & SHELL_DEBUG_BACKTRACE_WARNINGS) && + ((log_level & G_LOG_LEVEL_CRITICAL) || + (log_level & G_LOG_LEVEL_WARNING))) + gjs_dumpstack (); } static void @@ -406,6 +431,8 @@ main (int argc, char **argv) g_setenv ("GJS_DEBUG_OUTPUT", "stderr", TRUE); g_setenv ("GJS_DEBUG_TOPICS", "JS ERROR;JS LOG", TRUE); + shell_init_debug (g_getenv ("SHELL_DEBUG")); + shell_dbus_init (meta_get_replace_current_wm ()); shell_a11y_init (); shell_perf_log_init (); @@ -419,6 +446,7 @@ main (int argc, char **argv) tp_debug_set_flags ("all"); sender = tp_debug_sender_dup (); + g_log_set_default_handler (default_log_handler, sender); /* Initialize the global object */