diff --git a/awesome.c b/awesome.c index bc73e337d..413b64c90 100644 --- a/awesome.c +++ b/awesome.c @@ -145,6 +145,9 @@ awesome_atexit(bool restart) /* Disconnect *after* closing lua */ xcb_cursor_context_free(globalconf.cursor_ctx); +#ifdef WITH_XCB_ERRORS + xcb_errors_context_free(globalconf.errors_ctx); +#endif xcb_disconnect(globalconf.connection); close(sigchld_pipe[0]); @@ -751,6 +754,11 @@ main(int argc, char **argv) globalconf.visual->visual_id); } +#ifdef WITH_XCB_ERRORS + if (xcb_errors_context_new(globalconf.connection, &globalconf.errors_ctx) < 0) + fatal("Failed to initialize xcb-errors"); +#endif + /* Get a recent timestamp */ acquire_timestamp(); diff --git a/awesomeConfig.cmake b/awesomeConfig.cmake index 8d903161b..4592001c0 100644 --- a/awesomeConfig.cmake +++ b/awesomeConfig.cmake @@ -13,6 +13,7 @@ autoOption(GENERATE_MANPAGES "generate manpages") option(COMPRESS_MANPAGES "compress manpages" ON) option(GENERATE_DOC "generate API documentation" ON) option(DO_COVERAGE "build with coverage" OFF) +autoOption(WITH_XCB_ERRORS "build with xcb-errors") if (GENERATE_DOC AND DO_COVERAGE) message(STATUS "Not generating API documentation with DO_COVERAGE") set(GENERATE_DOC OFF) @@ -213,6 +214,16 @@ if(WITH_DBUS) autoDisable(WITH_DBUS "DBus not found.") endif() endif() + +if(WITH_XCB_ERRORS) + pkg_check_modules(XCB_ERRORS xcb-errors) + if(XCB_ERRORS_FOUND) + set(AWESOME_OPTIONAL_LDFLAGS ${AWESOME_OPTIONAL_LDFLAGS} ${XCB_ERRORS_LDFLAGS}) + set(AWESOME_OPTIONAL_INCLUDE_DIRS ${AWESOME_OPTIONAL_INCLUDE_DIRS} ${XCB_ERRORS_INCLUDE_DIRS}) + else() + autoDisable(WITH_XCB_ERRORS "xcb-errors not found.") + endif() +endif() # }}} # {{{ Install path and configuration variables diff --git a/common/version.c b/common/version.c index 0a5ff1f2d..00833a952 100644 --- a/common/version.c +++ b/common/version.c @@ -54,6 +54,11 @@ eprint_version(void) #else const char *has_dbus = "✘"; #endif +#ifdef WITH_XCB_ERRORS + const char *has_xcb_errors = "✔"; +#else + const char *has_xcb_errors = "✘"; +#endif #ifdef HAS_EXECINFO const char *has_execinfo = "✔"; #else @@ -63,12 +68,13 @@ eprint_version(void) printf("awesome %s (%s)\n" " • Compiled against %s (running with %s)\n" " • D-Bus support: %s\n" + " • xcb-errors support: %s\n" " • execinfo support: %s\n" " • xcb-randr version: %d.%d\n" " • LGI version: %s\n", AWESOME_VERSION, AWESOME_RELEASE, LUA_RELEASE, lua_tostring(L, -2), - has_dbus, has_execinfo, + has_dbus, has_xcb_errors, has_execinfo, XCB_RANDR_MAJOR_VERSION, XCB_RANDR_MINOR_VERSION, lua_tostring(L, -1)); lua_close(L); diff --git a/config.h b/config.h index 3ec9d7677..1ecc79ac2 100644 --- a/config.h +++ b/config.h @@ -8,6 +8,7 @@ #define AWESOME_DEFAULT_CONF "@AWESOME_SYSCONFDIR@/rc.lua" #cmakedefine WITH_DBUS +#cmakedefine WITH_XCB_ERRORS #cmakedefine HAS_EXECINFO #endif //_CONFIG_H_ diff --git a/docs/01-readme.md b/docs/01-readme.md index 7a997d5a8..d83d5b284 100644 --- a/docs/01-readme.md +++ b/docs/01-readme.md @@ -102,6 +102,8 @@ Additionally, the following optional dependencies exist: generate slightly better backtraces on crashes - `Xephyr` or `Xvfb` for running integration tests - [GTK+ >= 3.10](https://www.gtk.org/) for `./themes/gtk/` +- [xcb-errors](https://gitlab.freedesktop.org/xorg/lib/libxcb-errors) for + pretty-printing of X11 errors ## Running Awesome diff --git a/event.c b/event.c index 94b6b8fd7..989c0110c 100644 --- a/event.c +++ b/event.c @@ -1036,10 +1036,24 @@ xerror(xcb_generic_error_t *e) && e->major_code == XCB_CONFIGURE_WINDOW)) return; - warn("X error: request=%s (major %d, minor %d), error=%s (%d)", - xcb_event_get_request_label(e->major_code), +#ifdef WITH_XCB_ERRORS + const char *major = xcb_errors_get_name_for_major_code( + globalconf.errors_ctx, e->major_code); + const char *minor = xcb_errors_get_name_for_minor_code( + globalconf.errors_ctx, e->major_code, e->minor_code); + const char *extension = NULL; + const char *error = xcb_errors_get_name_for_error( + globalconf.errors_ctx, e->error_code, &extension); +#else + const char *major = xcb_event_get_request_label(e->major_code); + const char *minor = NULL; + const char *extension = NULL; + const char *error = xcb_event_get_error_label(e->error_code); +#endif + warn("X error: request=%s%s%s (major %d, minor %d), error=%s%s%s (%d)", + major, minor == NULL ? "" : "-", NONULL(minor), e->major_code, e->minor_code, - xcb_event_get_error_label(e->error_code), + NONULL(extension), extension == NULL ? "" : "-", error, e->error_code); return; diff --git a/globalconf.h b/globalconf.h index 6ef0d2062..aec479f8f 100644 --- a/globalconf.h +++ b/globalconf.h @@ -33,6 +33,11 @@ #include #include +#include "config.h" +#ifdef WITH_XCB_ERRORS +#include +#endif + #include "objects/key.h" #include "common/xembed.h" #include "common/buffer.h" @@ -82,6 +87,10 @@ typedef struct int default_screen; /** xcb-cursor context */ xcb_cursor_context_t *cursor_ctx; +#ifdef WITH_XCB_ERRORS + /** xcb-errors context */ + xcb_errors_context_t *errors_ctx; +#endif /** Keys symbol table */ xcb_key_symbols_t *keysyms; /** Logical screens */