]> git.sur5r.net Git - i3/i3/commitdiff
Make i3 compatible with the very latest xcb
authorMichael Stapelberg <michael@stapelberg.de>
Fri, 18 Mar 2011 13:36:36 +0000 (14:36 +0100)
committerMichael Stapelberg <michael@stapelberg.de>
Fri, 18 Mar 2011 13:39:27 +0000 (14:39 +0100)
This involves:
 • Compiling with xcb-util instead of xcb-{atom,aux} (they merged the libraries)
 • Not using xcb-{event,property} anymore (code removed upstream)
 • Not using the predefined WINDOW, CARDINEL, … atoms (removed upstream)
 • Using the new xcb_icccm_* data types/functions instead of just xcb_*
   (for example xcb_icccm_get_wm_hints instead of xcb_get_wm_hints)

Also I refactored the atoms to use x-macros.

20 files changed:
common.mk
include/all.h
include/atoms.xmacro [new file with mode: 0644]
include/data.h
include/handlers.h
include/i3.h
include/manage.h
include/util.h
include/workspace.h
include/xcb.h
include/xcb_compat.h [new file with mode: 0644]
src/con.c
src/ewmh.c
src/floating.c
src/handlers.c
src/main.c
src/manage.c
src/sighandler.c
src/window.c
src/x.c

index a9bab084c7bb0e4b34369072b827de0e9dd09993..db887cac9e5c576947061e848abae6c5f13b6160 100644 (file)
--- a/common.mk
+++ b/common.mk
@@ -11,6 +11,10 @@ endif
 GIT_VERSION:="$(shell git describe --tags --always) ($(shell git log --pretty=format:%cd --date=short -n1), branch $(shell [ -f .git/HEAD ] && sed 's/ref: refs\/heads\/\(.*\)/\\\\\\"\1\\\\\\"/g' .git/HEAD || echo 'unknown'))"
 VERSION:=$(shell git describe --tags --abbrev=0)
 
+ifeq ($(shell which pkg-config 2>/dev/null 1>/dev/null || echo 1),1)
+$(error "pkg-config was not found")
+endif
+
 # An easier way to get CFLAGS and LDFLAGS falling back in case there's
 # no pkg-config support for certain libraries
 cflags_for_lib = $(shell pkg-config --silence-errors --cflags $(1))
@@ -24,11 +28,14 @@ CFLAGS += -Wall
 CFLAGS += -Wunused-value
 CFLAGS += -Iinclude
 CFLAGS += -I/usr/local/include
-CFLAGS += $(call cflags_for_lib, xcb-event)
-CFLAGS += $(call cflags_for_lib, xcb-property)
 CFLAGS += $(call cflags_for_lib, xcb-keysyms)
+ifeq ($(shell pkg-config --exists xcb-util || echo 1),1)
+CFLAGS += -DXCB_COMPAT
 CFLAGS += $(call cflags_for_lib, xcb-atom)
 CFLAGS += $(call cflags_for_lib, xcb-aux)
+else
+CFLAGS += $(call cflags_for_lib, xcb-util)
+endif
 CFLAGS += $(call cflags_for_lib, xcb-icccm)
 CFLAGS += $(call cflags_for_lib, xcb-xinerama)
 CFLAGS += $(call cflags_for_lib, xcb-randr)
@@ -44,8 +51,12 @@ LDFLAGS += -lm
 LDFLAGS += $(call ldflags_for_lib, xcb-event, xcb-event)
 LDFLAGS += $(call ldflags_for_lib, xcb-property, xcb-property)
 LDFLAGS += $(call ldflags_for_lib, xcb-keysyms, xcb-keysyms)
+ifeq ($(shell pkg-config --exists xcb-util || echo 1),1)
 LDFLAGS += $(call ldflags_for_lib, xcb-atom, xcb-atom)
 LDFLAGS += $(call ldflags_for_lib, xcb-aux, xcb-aux)
+else
+LDFLAGS += $(call ldflags_for_lib, xcb-util)
+endif
 LDFLAGS += $(call ldflags_for_lib, xcb-icccm, xcb-icccm)
 LDFLAGS += $(call ldflags_for_lib, xcb-xinerama, xcb-xinerama)
 LDFLAGS += $(call ldflags_for_lib, xcb-randr, xcb-randr)
index 6251932c0b5794214fae74b0b326e27e75297dba..9d13bb956e6e8a6997aa0df2644ffdae6cc6a956 100644 (file)
 
 #include <xcb/xcb.h>
 #include <xcb/xcb_aux.h>
-#include <xcb/xcb_event.h>
 #include <xcb/xcb_keysyms.h>
 #include <xcb/xcb_icccm.h>
 
+/* Contains compatibility definitions for old libxcb versions */
+#ifdef XCB_COMPAT
+#include "xcb_compat.h"
+#endif
+
 #include "util.h"
 #include "ipc.h"
 #include "tree.h"
diff --git a/include/atoms.xmacro b/include/atoms.xmacro
new file mode 100644 (file)
index 0000000..2543ffd
--- /dev/null
@@ -0,0 +1,31 @@
+xmacro(_NET_SUPPORTED)
+xmacro(_NET_SUPPORTING_WM_CHECK)
+xmacro(_NET_WM_NAME)
+xmacro(_NET_WM_STATE_FULLSCREEN)
+xmacro(_NET_WM_STATE)
+xmacro(_NET_WM_WINDOW_TYPE)
+xmacro(_NET_WM_WINDOW_TYPE_DOCK)
+xmacro(_NET_WM_WINDOW_TYPE_DIALOG)
+xmacro(_NET_WM_WINDOW_TYPE_UTILITY)
+xmacro(_NET_WM_WINDOW_TYPE_TOOLBAR)
+xmacro(_NET_WM_WINDOW_TYPE_SPLASH)
+xmacro(_NET_WM_DESKTOP)
+xmacro(_NET_WM_STRUT_PARTIAL)
+xmacro(WM_PROTOCOLS)
+xmacro(WM_DELETE_WINDOW)
+xmacro(UTF8_STRING)
+xmacro(WM_STATE)
+xmacro(WM_CLIENT_LEADER)
+xmacro(_NET_CURRENT_DESKTOP)
+xmacro(_NET_ACTIVE_WINDOW)
+xmacro(_NET_WORKAREA)
+xmacro(WM_TAKE_FOCUS)
+xmacro(WM_HINTS)
+xmacro(WM_NORMAL_HINTS)
+xmacro(WM_TRANSIENT_FOR)
+xmacro(ATOM)
+xmacro(WINDOW)
+xmacro(WM_NAME)
+xmacro(WM_CLASS)
+xmacro(STRING)
+xmacro(CARDINAL)
index 7cbf3dd66ce18c26db049c3db01fdef67b7ee43f..8beb91ab5f7f73a8d020afb55f8ac25d73f0b454 100644 (file)
@@ -7,7 +7,6 @@
  * include/data.h: This file defines all data structures used by i3
  *
  */
-#include <xcb/xcb.h>
 #include <xcb/randr.h>
 #include <xcb/xcb_atom.h>
 #include <stdbool.h>
index 76ba3eeaf2996c10278b76b6a8630958f69ad8fa..1c8aa283291fba33a03b9c84763b36efdc782108 100644 (file)
 
 #include <xcb/randr.h>
 
+extern int randr_base;
 
 void add_ignore_event(const int sequence);
 
+/**
+ * Takes an xcb_generic_event_t and calls the appropriate handler, based on the
+ * event type.
+ *
+ */
+void handle_event(int type, xcb_generic_event_t *event);
+
+/**
+ * Sets the appropriate atoms for the property handlers after the atoms were
+ * received from X11
+ *
+ */
+void property_handlers_init();
+
 /**
  * There was a key press. We compare this key code with our bindings table and
  * pass the bound action to parse_command().
index 3c238c46d051dea77e725251f9e5b34f18b9d4ec..060a0cf847838a444d7b78cb4f7e6bc7f4b29db7 100644 (file)
@@ -8,9 +8,6 @@
  * See file LICENSE for license information.
  *
  */
-#include <xcb/xcb.h>
-#include <xcb/xcb_property.h>
-#include <xcb/xcb_event.h>
 #include <xcb/xcb_keysyms.h>
 
 #include <X11/XKBlib.h>
@@ -31,11 +28,8 @@ extern TAILQ_HEAD(bindings_head, Binding) *bindings;
 extern TAILQ_HEAD(autostarts_head, Autostart) autostarts;
 extern TAILQ_HEAD(assignments_head, Assignment) assignments;
 extern SLIST_HEAD(stack_wins_head, Stack_Window) stack_wins;
-extern xcb_event_handlers_t evenths;
-extern xcb_property_handlers_t prophs;
 extern uint8_t root_depth;
 extern bool xcursor_supported, xkb_supported;
-extern xcb_atom_t atoms[NUM_ATOMS];
 extern xcb_window_t root;
 
 #endif
index 555cefbed4e0d06a7a9a71bdcd02f922e57a51e7..e23eccf36a9960f19712061e4471911754ff9f7b 100644 (file)
@@ -8,7 +8,6 @@
  * See file LICENSE for license information.
  *
  */
-#include <xcb/xcb.h>
 
 #include "data.h"
 
index 064a4792d8cb4a4635352a5bfae91ac51ee10e90..514e10bde2884265fe59452c6de7b9202feda8a3 100644 (file)
@@ -8,7 +8,6 @@
  * See file LICENSE for license information.
  *
  */
-#include <xcb/xcb.h>
 #include <err.h>
 
 #include "data.h"
index ae43e2f1a80bb487c27e6e7fc6d78b9a5b1b1501..2132a7922915dbb8c5071b0abee78e8ba3cf046b 100644 (file)
@@ -8,7 +8,6 @@
  * See file LICENSE for license information.
  *
  */
-#include <xcb/xcb.h>
 
 #include "data.h"
 #include "tree.h"
index 47eec76b6be0d69999d5c8b602e2417e2763490c..bec06b06269e88821729095947733634477e2b7d 100644 (file)
                           XCB_EVENT_MASK_SUBSTRUCTURE_NOTIFY |   /* …subwindows get notifies */ \
                           XCB_EVENT_MASK_ENTER_WINDOW)           /* …user moves cursor inside our window */
 
-
-enum {
-    _NET_SUPPORTED = 0,
-    _NET_SUPPORTING_WM_CHECK,
-    _NET_WM_NAME,
-    _NET_WM_STATE_FULLSCREEN,
-    _NET_WM_STATE,
-    _NET_WM_WINDOW_TYPE,
-    _NET_WM_WINDOW_TYPE_DOCK,
-    _NET_WM_WINDOW_TYPE_DIALOG,
-    _NET_WM_WINDOW_TYPE_UTILITY,
-    _NET_WM_WINDOW_TYPE_TOOLBAR,
-    _NET_WM_WINDOW_TYPE_SPLASH,
-    _NET_WM_DESKTOP,
-    _NET_WM_STRUT_PARTIAL,
-    WM_PROTOCOLS,
-    WM_DELETE_WINDOW,
-    UTF8_STRING,
-    WM_STATE,
-    WM_CLIENT_LEADER,
-    _NET_CURRENT_DESKTOP,
-    _NET_ACTIVE_WINDOW,
-    _NET_WORKAREA,
-    WM_TAKE_FOCUS,
-    NUM_ATOMS
-};
+#define xmacro(atom) xcb_atom_t A_ ## atom;
+#include "atoms.xmacro"
+#undef xmacro
 
 extern unsigned int xcb_numlock_mask;
 
diff --git a/include/xcb_compat.h b/include/xcb_compat.h
new file mode 100644 (file)
index 0000000..736cbb9
--- /dev/null
@@ -0,0 +1,24 @@
+#ifndef _XCB_COMPAT_H
+#define _XCB_COMPAT_H
+
+#define xcb_icccm_get_wm_protocols_reply_t xcb_get_wm_protocols_reply_t
+#define xcb_icccm_get_wm_protocols_unchecked xcb_get_wm_protocols_unchecked
+#define xcb_icccm_get_wm_protocols_reply xcb_get_wm_protocols_reply
+#define xcb_icccm_get_wm_protocols_reply_wipe xcb_get_wm_protocols_reply_wipe
+#define XCB_ICCCM_WM_STATE_NORMAL XCB_WM_STATE_NORMAL
+#define XCB_ICCCM_WM_STATE_WITHDRAWN XCB_WM_STATE_WITHDRAWN
+#define xcb_icccm_get_wm_size_hints_from_reply xcb_get_wm_size_hints_from_reply
+#define xcb_icccm_get_wm_normal_hints_reply xcb_get_wm_normal_hints_reply
+#define xcb_icccm_get_wm_normal_hints_unchecked xcb_get_wm_normal_hints_unchecked
+#define XCB_ICCCM_SIZE_HINT_P_MIN_SIZE XCB_SIZE_HINT_P_MIN_SIZE
+#define XCB_ICCCM_SIZE_HINT_P_RESIZE_INC XCB_SIZE_HINT_P_RESIZE_INC
+#define XCB_ICCCM_SIZE_HINT_BASE_SIZE XCB_SIZE_HINT_BASE_SIZE
+#define XCB_ICCCM_SIZE_HINT_P_ASPECT XCB_SIZE_HINT_P_ASPECT
+#define xcb_icccm_wm_hints_t xcb_wm_hints_t
+#define xcb_icccm_get_wm_hints_from_reply xcb_get_wm_hints_from_reply
+#define xcb_icccm_get_wm_hints_reply xcb_get_wm_hints_reply
+#define xcb_icccm_get_wm_hints_unchecked xcb_get_wm_hints_unchecked
+#define xcb_icccm_wm_hints_get_urgency xcb_wm_hints_get_urgency
+#define xcb_icccm_get_wm_transient_for_from_reply xcb_get_wm_transient_for_from_reply
+
+#endif
index e1359069f6df3102ce676fa1d15ec983fa935fd5..8c0a8303d497c14a5d7a3f0052a7c620e8740b12 100644 (file)
--- a/src/con.c
+++ b/src/con.c
@@ -504,10 +504,10 @@ void con_toggle_fullscreen(Con *con) {
     unsigned int num = 0;
 
     if (con->fullscreen_mode != CF_NONE)
-        values[num++] = atoms[_NET_WM_STATE_FULLSCREEN];
+        values[num++] = A__NET_WM_STATE_FULLSCREEN;
 
     xcb_change_property(conn, XCB_PROP_MODE_REPLACE, con->window->id,
-                        atoms[_NET_WM_STATE], ATOM, 32, num, values);
+                        A__NET_WM_STATE, A_ATOM, 32, num, values);
 }
 
 /*
index 67daa02231da9f1f9de7febb8e0fb0262a4641b3..7b2cc3e458fe03d754acae891d0ca48a61a72a20 100644 (file)
@@ -31,7 +31,7 @@ void ewmh_update_current_desktop() {
         TAILQ_FOREACH(ws, &(output_get_content(output)->nodes_head), nodes) {
             if (ws == focused_ws) {
                 xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root,
-                        atoms[_NET_CURRENT_DESKTOP], CARDINAL, 32, 1, &idx);
+                        A__NET_CURRENT_DESKTOP, A_CARDINAL, 32, 1, &idx);
                 return;
             }
             ++idx;
@@ -48,7 +48,7 @@ void ewmh_update_current_desktop() {
  */
 void ewmh_update_active_window(xcb_window_t window) {
     xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root,
-            atoms[_NET_ACTIVE_WINDOW], WINDOW, 32, 1, &window);
+            A__NET_ACTIVE_WINDOW, A_WINDOW, 32, 1, &window);
 }
 
 /*
@@ -104,7 +104,7 @@ void ewmh_update_workarea() {
         }
     }
     xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root,
-            atoms[_NET_WORKAREA], CARDINAL, 32,
+            A__NET_WORKAREA, A_CARDINAL, 32,
             num_workspaces * (sizeof(Rect) / sizeof(uint32_t)),
             workarea);
     free(workarea);
index ef500bf6d2e7f902134cded7990ff1e7e2115cd7..9d4e1cf8e438ff379bf9e9f2fbbd899dc8821936 100644 (file)
@@ -374,19 +374,15 @@ void drag_pointer(Con *con, xcb_button_press_event_t *event, xcb_window_t
     while ((inside_event = xcb_wait_for_event(conn))) {
         /* We now handle all events we can get using xcb_poll_for_event */
         do {
-            /* Same as get_event_handler in xcb */
-            int nr = inside_event->response_type;
-            if (nr == 0) {
-                /* An error occured */
-                //handle_event(NULL, conn, inside_event);
+            /* skip x11 errors */
+            if (inside_event->response_type == 0) {
                 free(inside_event);
                 continue;
             }
-            assert(nr < 256);
-            nr &= XCB_EVENT_RESPONSE_TYPE_MASK;
-            assert(nr >= 2);
+            /* Strip off the highest bit (set if the event is generated) */
+            int type = (inside_event->response_type & 0x7F);
 
-            switch (nr) {
+            switch (type) {
                 case XCB_BUTTON_RELEASE:
                     goto done;
 
@@ -398,13 +394,13 @@ void drag_pointer(Con *con, xcb_button_press_event_t *event, xcb_window_t
 
                 case XCB_UNMAP_NOTIFY:
                     DLOG("Unmap-notify, aborting\n");
-                    xcb_event_handle(&evenths, inside_event);
+                    handle_event(type, inside_event);
                     goto done;
 
                 default:
                     DLOG("Passing to original handler\n");
                     /* Use original handler */
-                    xcb_event_handle(&evenths, inside_event);
+                    handle_event(type, inside_event);
                     break;
             }
             if (last_motion_notify != inside_event)
index 6e6626a9671f275f7a51141b42857fabfb8ced75..111d7c24b8cca5b6d3adadb31e7a8c087d8684dd 100644 (file)
@@ -6,14 +6,19 @@
  *
  */
 #include <time.h>
+#include <limits.h>
 
-#include <xcb/xcb_atom.h>
 #include <xcb/randr.h>
 
 #include <X11/XKBlib.h>
 
 #include "all.h"
 
+int randr_base = -1;
+
+/* forward declaration for property_notify */
+static int property_notify(uint8_t state, xcb_window_t window, xcb_atom_t atom);
+
 /* After mapping/unmapping windows, a notify event is generated. However, we don’t want it,
    since it’d trigger an infinite loop of switching between the different windows when
    changing workspaces */
@@ -59,6 +64,143 @@ static bool event_is_ignored(const int sequence) {
     return false;
 }
 
+/*
+ * Takes an xcb_generic_event_t and calls the appropriate handler, based on the
+ * event type.
+ *
+ */
+void handle_event(int type, xcb_generic_event_t *event) {
+    /* XXX: remove the NULL and conn parameters as soon as this version of libxcb is required */
+
+    if (randr_base > -1 &&
+        type == randr_base + XCB_RANDR_SCREEN_CHANGE_NOTIFY) {
+        handle_screen_change(NULL, conn, event);
+        return;
+    }
+
+    switch (type) {
+        case XCB_KEY_PRESS:
+            handle_key_press(NULL, conn, (xcb_key_press_event_t*)event);
+            break;
+
+        case XCB_BUTTON_PRESS:
+            handle_button_press(NULL, conn, (xcb_button_press_event_t*)event);
+            break;
+
+        case XCB_MAP_REQUEST:
+            handle_map_request(NULL, conn, (xcb_map_request_event_t*)event);
+            break;
+
+        case XCB_UNMAP_NOTIFY:
+            handle_unmap_notify_event(NULL, conn, (xcb_unmap_notify_event_t*)event);
+            break;
+
+        case XCB_DESTROY_NOTIFY:
+            handle_destroy_notify_event(NULL, conn, (xcb_destroy_notify_event_t*)event);
+            break;
+
+        case XCB_EXPOSE:
+            handle_expose_event(NULL, conn, (xcb_expose_event_t*)event);
+            break;
+
+        case XCB_MOTION_NOTIFY:
+            handle_motion_notify(NULL, conn, (xcb_motion_notify_event_t*)event);
+            break;
+
+        /* Enter window = user moved his mouse over the window */
+        case XCB_ENTER_NOTIFY:
+            handle_enter_notify(NULL, conn, (xcb_enter_notify_event_t*)event);
+            break;
+
+        /* Client message are sent to the root window. The only interesting
+         * client message for us is _NET_WM_STATE, we honour
+         * _NET_WM_STATE_FULLSCREEN */
+        case XCB_CLIENT_MESSAGE:
+            handle_client_message(NULL, conn, (xcb_client_message_event_t*)event);
+            break;
+
+        /* Configure request = window tried to change size on its own */
+        case XCB_CONFIGURE_REQUEST:
+            handle_configure_request(NULL, conn, (xcb_configure_request_event_t*)event);
+            break;
+
+        /* Mapping notify = keyboard mapping changed (Xmodmap), re-grab bindings */
+        case XCB_MAPPING_NOTIFY:
+            handle_mapping_notify(NULL, conn, (xcb_mapping_notify_event_t*)event);
+            break;
+
+        case XCB_PROPERTY_NOTIFY:
+            DLOG("Property notify\n");
+            xcb_property_notify_event_t *e = (xcb_property_notify_event_t*)event;
+            property_notify(e->state, e->window, e->atom);
+            break;
+
+        default:
+            DLOG("Unhandled event of type %d\n", type);
+            break;
+    }
+}
+
+typedef int (*cb_property_handler_t)(void *data, xcb_connection_t *c, uint8_t state, xcb_window_t window, xcb_atom_t atom, xcb_get_property_reply_t *property);
+
+struct property_handler_t {
+    xcb_atom_t atom;
+    uint32_t long_len;
+    cb_property_handler_t cb;
+};
+
+static struct property_handler_t property_handlers[] = {
+    { 0, 128, handle_windowname_change },
+    { 0, UINT_MAX, handle_hints },
+    { 0, 128, handle_windowname_change_legacy },
+    { 0, UINT_MAX, handle_normal_hints },
+    { 0, UINT_MAX, handle_clientleader_change },
+    { 0, UINT_MAX, handle_transient_for }
+};
+#define NUM_HANDLERS (sizeof(property_handlers) / sizeof(struct property_handler_t))
+
+/*
+ * Sets the appropriate atoms for the property handlers after the atoms were
+ * received from X11
+ *
+ */
+void property_handlers_init() {
+    property_handlers[0].atom = A__NET_WM_NAME;
+    property_handlers[1].atom = A_WM_HINTS;
+    property_handlers[2].atom = A_WM_NAME;
+    property_handlers[3].atom = A_WM_NORMAL_HINTS;
+    property_handlers[4].atom = A_WM_CLIENT_LEADER;
+    property_handlers[5].atom = A_WM_TRANSIENT_FOR;
+}
+
+static int property_notify(uint8_t state, xcb_window_t window, xcb_atom_t atom) {
+    struct property_handler_t *handler = NULL;
+    xcb_get_property_reply_t *propr = NULL;
+    int ret;
+
+    for (int c = 0; c < sizeof(property_handlers) / sizeof(struct property_handler_t); c++) {
+        if (property_handlers[c].atom != atom)
+            continue;
+
+        handler = &property_handlers[c];
+        break;
+    }
+
+    if (handler == NULL) {
+        DLOG("Unhandled property notify for atom %d (0x%08x)\n", atom, atom);
+        return 0;
+    }
+
+    if (state != XCB_PROPERTY_DELETE) {
+        xcb_get_property_cookie_t cookie = xcb_get_property(conn, 0, window, atom, XCB_GET_PROPERTY_TYPE_ANY, 0, handler->long_len);
+        propr = xcb_get_property_reply(conn, cookie, 0);
+    }
+
+    ret = handler->cb(NULL, conn, state, window, atom, propr);
+    FREE(propr);
+    return ret;
+}
+
 /*
  * There was a key press. We compare this key code with our bindings table and pass
  * the bound action to parse_command().
@@ -627,10 +769,10 @@ int handle_expose_event(void *data, xcb_connection_t *conn, xcb_expose_event_t *
  */
 int handle_client_message(void *data, xcb_connection_t *conn, xcb_client_message_event_t *event) {
     LOG("ClientMessage for window 0x%08x\n", event->window);
-    if (event->type == atoms[_NET_WM_STATE]) {
-        if (event->format != 32 || event->data.data32[1] != atoms[_NET_WM_STATE_FULLSCREEN]) {
+    if (event->type == A__NET_WM_STATE) {
+        if (event->format != 32 || event->data.data32[1] != A__NET_WM_STATE_FULLSCREEN) {
             DLOG("atom in clientmessage is %d, fullscreen is %d\n",
-                    event->data.data32[1], atoms[_NET_WM_STATE_FULLSCREEN]);
+                    event->data.data32[1], A__NET_WM_STATE_FULLSCREEN);
             DLOG("not about fullscreen atom\n");
             return 0;
         }
@@ -693,17 +835,17 @@ int handle_normal_hints(void *data, xcb_connection_t *conn, uint8_t state, xcb_w
 
     /* If the hints were already in this event, use them, if not, request them */
     if (reply != NULL)
-        xcb_get_wm_size_hints_from_reply(&size_hints, reply);
+        xcb_icccm_get_wm_size_hints_from_reply(&size_hints, reply);
     else
-        xcb_get_wm_normal_hints_reply(conn, xcb_get_wm_normal_hints_unchecked(conn, con->window->id), &size_hints, NULL);
+        xcb_icccm_get_wm_normal_hints_reply(conn, xcb_icccm_get_wm_normal_hints_unchecked(conn, con->window->id), &size_hints, NULL);
 
-    if ((size_hints.flags & XCB_SIZE_HINT_P_MIN_SIZE)) {
+    if ((size_hints.flags & XCB_ICCCM_SIZE_HINT_P_MIN_SIZE)) {
         // TODO: Minimum size is not yet implemented
         DLOG("Minimum size: %d (width) x %d (height)\n", size_hints.min_width, size_hints.min_height);
     }
 
     bool changed = false;
-    if ((size_hints.flags & XCB_SIZE_HINT_P_RESIZE_INC)) {
+    if ((size_hints.flags & XCB_ICCCM_SIZE_HINT_P_RESIZE_INC)) {
         if (size_hints.width_inc > 0 && size_hints.width_inc < 0xFFFF)
             if (con->width_increment != size_hints.width_inc) {
                 con->width_increment = size_hints.width_inc;
@@ -724,10 +866,10 @@ int handle_normal_hints(void *data, xcb_connection_t *conn, uint8_t state, xcb_w
     /* base_width/height are the desired size of the window.
        We check if either the program-specified size or the program-specified
        min-size is available */
-    if (size_hints.flags & XCB_SIZE_HINT_BASE_SIZE) {
+    if (size_hints.flags & XCB_ICCCM_SIZE_HINT_BASE_SIZE) {
         base_width = size_hints.base_width;
         base_height = size_hints.base_height;
-    } else if (size_hints.flags & XCB_SIZE_HINT_P_MIN_SIZE) {
+    } else if (size_hints.flags & XCB_ICCCM_SIZE_HINT_P_MIN_SIZE) {
         /* TODO: is this right? icccm says not */
         base_width = size_hints.min_width;
         base_height = size_hints.min_height;
@@ -742,7 +884,7 @@ int handle_normal_hints(void *data, xcb_connection_t *conn, uint8_t state, xcb_w
     }
 
     /* If no aspect ratio was set or if it was invalid, we ignore the hints */
-    if (!(size_hints.flags & XCB_SIZE_HINT_P_ASPECT) ||
+    if (!(size_hints.flags & XCB_ICCCM_SIZE_HINT_P_ASPECT) ||
         (size_hints.min_aspect_num <= 0) ||
         (size_hints.min_aspect_den <= 0)) {
         goto render_and_return;
@@ -788,13 +930,13 @@ int handle_hints(void *data, xcb_connection_t *conn, uint8_t state, xcb_window_t
         return 1;
     }
 
-    xcb_wm_hints_t hints;
+    xcb_icccm_wm_hints_t hints;
 
     if (reply != NULL) {
-        if (!xcb_get_wm_hints_from_reply(&hints, reply))
+        if (!xcb_icccm_get_wm_hints_from_reply(&hints, reply))
             return 1;
     } else {
-        if (!xcb_get_wm_hints_reply(conn, xcb_get_wm_hints_unchecked(conn, con->window->id), &hints, NULL))
+        if (!xcb_icccm_get_wm_hints_reply(conn, xcb_icccm_get_wm_hints_unchecked(conn, con->window->id), &hints, NULL))
             return 1;
     }
 
@@ -804,7 +946,7 @@ int handle_hints(void *data, xcb_connection_t *conn, uint8_t state, xcb_window_t
     }
 
     /* Update the flag on the client directly */
-    con->urgent = (xcb_wm_hints_get_urgency(&hints) != 0);
+    con->urgent = (xcb_icccm_wm_hints_get_urgency(&hints) != 0);
     //CLIENT_LOG(con);
     LOG("Urgency flag changed to %d\n", con->urgent);
 
@@ -841,7 +983,7 @@ int handle_transient_for(void *data, xcb_connection_t *conn, uint8_t state, xcb_
 
     if (prop == NULL) {
         prop = xcb_get_property_reply(conn, xcb_get_property_unchecked(conn,
-                                false, window, WM_TRANSIENT_FOR, WINDOW, 0, 32), NULL);
+                                false, window, A_WM_TRANSIENT_FOR, A_WINDOW, 0, 32), NULL);
         if (prop == NULL)
             return 1;
     }
@@ -872,7 +1014,7 @@ int handle_clientleader_change(void *data, xcb_connection_t *conn, uint8_t state
 
     if (prop == NULL) {
         prop = xcb_get_property_reply(conn, xcb_get_property_unchecked(conn,
-                                false, window, WM_CLIENT_LEADER, WINDOW, 0, 32), NULL);
+                                false, window, A_WM_CLIENT_LEADER, A_WINDOW, 0, 32), NULL);
         if (prop == NULL)
             return 1;
     }
index 002eb6a5729a93df1988f1bd7121baef09b5d097..16df027bcc4690df0043af1b0becff16866df30d 100644 (file)
@@ -15,9 +15,6 @@ extern Con *focused;
 char **start_argv;
 
 xcb_connection_t *conn;
-xcb_event_handlers_t evenths;
-xcb_property_handlers_t prophs;
-xcb_atom_t atoms[NUM_ATOMS];
 
 xcb_window_t root;
 uint8_t root_depth;
@@ -66,8 +63,17 @@ static void xcb_check_cb(EV_P_ ev_check *w, int revents) {
     xcb_generic_event_t *event;
 
     while ((event = xcb_poll_for_event(conn)) != NULL) {
-            xcb_event_handle(&evenths, event);
-            free(event);
+        if (event->response_type == 0) {
+            ELOG("X11 Error received! sequence %x\n", event->sequence);
+            continue;
+        }
+
+        /* Strip off the highest bit (set if the event is generated) */
+        int type = (event->response_type & 0x7F);
+
+        handle_event(type, event);
+
+        free(event);
     }
 }
 
@@ -149,7 +155,6 @@ int main(int argc, char *argv[]) {
     bool only_check_config = false;
     bool force_xinerama = false;
     bool disable_signalhandler = false;
-    xcb_intern_atom_cookie_t atom_cookies[NUM_ATOMS];
     static struct option long_options[] = {
         {"no-autostart", no_argument, 0, 'a'},
         {"config", required_argument, 0, 'c'},
@@ -272,30 +277,10 @@ int main(int argc, char *argv[]) {
     check_error(conn, cookie, "Another window manager seems to be running");
 
     /* Place requests for the atoms we need as soon as possible */
-    #define REQUEST_ATOM(name) atom_cookies[name] = xcb_intern_atom(conn, 0, strlen(#name), #name);
-
-    REQUEST_ATOM(_NET_SUPPORTED);
-    REQUEST_ATOM(_NET_WM_STATE_FULLSCREEN);
-    REQUEST_ATOM(_NET_SUPPORTING_WM_CHECK);
-    REQUEST_ATOM(_NET_WM_NAME);
-    REQUEST_ATOM(_NET_WM_STATE);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE);
-    REQUEST_ATOM(_NET_WM_DESKTOP);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE_DOCK);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE_DIALOG);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE_UTILITY);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE_TOOLBAR);
-    REQUEST_ATOM(_NET_WM_WINDOW_TYPE_SPLASH);
-    REQUEST_ATOM(_NET_WM_STRUT_PARTIAL);
-    REQUEST_ATOM(WM_PROTOCOLS);
-    REQUEST_ATOM(WM_DELETE_WINDOW);
-    REQUEST_ATOM(UTF8_STRING);
-    REQUEST_ATOM(WM_STATE);
-    REQUEST_ATOM(WM_CLIENT_LEADER);
-    REQUEST_ATOM(_NET_CURRENT_DESKTOP);
-    REQUEST_ATOM(_NET_ACTIVE_WINDOW);
-    REQUEST_ATOM(_NET_WORKAREA);
-    REQUEST_ATOM(WM_TAKE_FOCUS);
+    #define xmacro(atom) \
+        xcb_intern_atom_cookie_t atom ## _cookie = xcb_intern_atom(conn, 0, strlen(#atom), #atom);
+    #include "atoms.xmacro"
+    #undef xmacro
 
     /* Initialize the Xlib connection */
     xlibdpy = xkbdpy = XOpenDisplay(NULL);
@@ -338,95 +323,32 @@ int main(int argc, char *argv[]) {
         }
     }
 
-    memset(&evenths, 0, sizeof(xcb_event_handlers_t));
-    memset(&prophs, 0, sizeof(xcb_property_handlers_t));
-
-    xcb_event_handlers_init(conn, &evenths);
-    xcb_property_handlers_init(&prophs, &evenths);
-    xcb_event_set_key_press_handler(&evenths, handle_key_press, NULL);
-
-    xcb_event_set_button_press_handler(&evenths, handle_button_press, NULL);
-
-    xcb_event_set_map_request_handler(&evenths, handle_map_request, NULL);
-
-    xcb_event_set_unmap_notify_handler(&evenths, handle_unmap_notify_event, NULL);
-    xcb_event_set_destroy_notify_handler(&evenths, handle_destroy_notify_event, NULL);
-
-    xcb_event_set_expose_handler(&evenths, handle_expose_event, NULL);
-
-    xcb_event_set_motion_notify_handler(&evenths, handle_motion_notify, NULL);
-
-    /* Enter window = user moved his mouse over the window */
-    xcb_event_set_enter_notify_handler(&evenths, handle_enter_notify, NULL);
-
-    /* Client message are sent to the root window. The only interesting client message
-       for us is _NET_WM_STATE, we honour _NET_WM_STATE_FULLSCREEN */
-    xcb_event_set_client_message_handler(&evenths, handle_client_message, NULL);
-
-    /* Configure request = window tried to change size on its own */
-    xcb_event_set_configure_request_handler(&evenths, handle_configure_request, NULL);
-
     /* Setup NetWM atoms */
-    #define GET_ATOM(name) \
+    #define xmacro(name) \
         do { \
-            xcb_intern_atom_reply_t *reply = xcb_intern_atom_reply(conn, atom_cookies[name], NULL); \
+            xcb_intern_atom_reply_t *reply = xcb_intern_atom_reply(conn, name ## _cookie, NULL); \
             if (!reply) { \
                 ELOG("Could not get atom " #name "\n"); \
                 exit(-1); \
             } \
-            atoms[name] = reply->atom; \
+            A_ ## name = reply->atom; \
             free(reply); \
-        } while (0)
-
-    GET_ATOM(_NET_SUPPORTED);
-    GET_ATOM(_NET_WM_STATE_FULLSCREEN);
-    GET_ATOM(_NET_SUPPORTING_WM_CHECK);
-    GET_ATOM(_NET_WM_NAME);
-    GET_ATOM(_NET_WM_STATE);
-    GET_ATOM(_NET_WM_WINDOW_TYPE);
-    GET_ATOM(_NET_WM_DESKTOP);
-    GET_ATOM(_NET_WM_WINDOW_TYPE_DOCK);
-    GET_ATOM(_NET_WM_WINDOW_TYPE_DIALOG);
-    GET_ATOM(_NET_WM_WINDOW_TYPE_UTILITY);
-    GET_ATOM(_NET_WM_WINDOW_TYPE_TOOLBAR);
-    GET_ATOM(_NET_WM_WINDOW_TYPE_SPLASH);
-    GET_ATOM(_NET_WM_STRUT_PARTIAL);
-    GET_ATOM(WM_PROTOCOLS);
-    GET_ATOM(WM_DELETE_WINDOW);
-    GET_ATOM(UTF8_STRING);
-    GET_ATOM(WM_STATE);
-    GET_ATOM(WM_CLIENT_LEADER);
-    GET_ATOM(_NET_CURRENT_DESKTOP);
-    GET_ATOM(_NET_ACTIVE_WINDOW);
-    GET_ATOM(_NET_WORKAREA);
-    GET_ATOM(WM_TAKE_FOCUS);
-
-    /* Watch _NET_WM_NAME (title of the window encoded in UTF-8) */
-    xcb_property_set_handler(&prophs, atoms[_NET_WM_NAME], 128, handle_windowname_change, NULL);
-
-    /* Watch WM_HINTS (contains the urgent property) */
-    xcb_property_set_handler(&prophs, WM_HINTS, UINT_MAX, handle_hints, NULL);
-
-    /* Watch WM_NAME (title of the window encoded in COMPOUND_TEXT) */
-    xcb_watch_wm_name(&prophs, 128, handle_windowname_change_legacy, NULL);
-
-    /* Watch WM_NORMAL_HINTS (aspect ratio, size increments, …) */
-    xcb_property_set_handler(&prophs, WM_NORMAL_HINTS, UINT_MAX, handle_normal_hints, NULL);
-
-    /* Watch WM_CLIENT_LEADER (= logical parent window for toolbars etc.) */
-    xcb_property_set_handler(&prophs, atoms[WM_CLIENT_LEADER], UINT_MAX, handle_clientleader_change, NULL);
-
-    /* Watch WM_TRANSIENT_FOR property (to which client this popup window belongs) */
-    xcb_property_set_handler(&prophs, WM_TRANSIENT_FOR, UINT_MAX, handle_transient_for, NULL);
-
-    /* Mapping notify = keyboard mapping changed (Xmodmap), re-grab bindings */
-    xcb_event_set_mapping_notify_handler(&evenths, handle_mapping_notify, NULL);
+        } while (0);
+    #include "atoms.xmacro"
+    #undef xmacro
+
+    property_handlers_init();
 
     /* Set up the atoms we support */
-    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, atoms[_NET_SUPPORTED], ATOM, 32, 7, atoms);
+    xcb_atom_t supported_atoms[] = {
+#define xmacro(atom) A_ ## atom,
+#include "atoms.xmacro"
+#undef xmacro
+    };
+    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, A__NET_SUPPORTED, A_ATOM, 32, 7, supported_atoms);
     /* Set up the window manager’s name */
-    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, atoms[_NET_SUPPORTING_WM_CHECK], WINDOW, 32, 1, &root);
-    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, atoms[_NET_WM_NAME], atoms[UTF8_STRING], 8, strlen("i3"), "i3");
+    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, A__NET_SUPPORTING_WM_CHECK, A_WINDOW, 32, 1, &root);
+    xcb_change_property(conn, XCB_PROP_MODE_REPLACE, root, A__NET_WM_NAME, A_UTF8_STRING, 8, strlen("i3"), "i3");
 
     keysyms = xcb_key_symbols_alloc(conn);
 
@@ -446,17 +368,11 @@ int main(int argc, char *argv[]) {
     if (needs_tree_init)
         tree_init();
 
-    int randr_base;
     if (force_xinerama) {
         xinerama_init();
     } else {
         DLOG("Checking for XRandR...\n");
         randr_init(&randr_base);
-
-        xcb_event_set_handler(&evenths,
-                              randr_base + XCB_RANDR_SCREEN_CHANGE_NOTIFY,
-                              handle_screen_change,
-                              NULL);
     }
 
     tree_render();
index c4d6172b99fefe5baa1b7a4899c5abeeedec544a..4821e28f76451e393b925adb8cab6cca6b634913 100644 (file)
@@ -85,15 +85,6 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
                               utf8_title_cookie, title_cookie,
                               class_cookie, leader_cookie, transient_cookie;
 
-    wm_type_cookie = xcb_get_any_property_unchecked(conn, false, window, atoms[_NET_WM_WINDOW_TYPE], UINT32_MAX);
-    strut_cookie = xcb_get_any_property_unchecked(conn, false, window, atoms[_NET_WM_STRUT_PARTIAL], UINT32_MAX);
-    state_cookie = xcb_get_any_property_unchecked(conn, false, window, atoms[_NET_WM_STATE], UINT32_MAX);
-    utf8_title_cookie = xcb_get_any_property_unchecked(conn, false, window, atoms[_NET_WM_NAME], 128);
-    leader_cookie = xcb_get_any_property_unchecked(conn, false, window, atoms[WM_CLIENT_LEADER], UINT32_MAX);
-    transient_cookie = xcb_get_any_property_unchecked(conn, false, window, WM_TRANSIENT_FOR, UINT32_MAX);
-    title_cookie = xcb_get_any_property_unchecked(conn, false, window, WM_NAME, 128);
-    class_cookie = xcb_get_any_property_unchecked(conn, false, window, WM_CLASS, 128);
-    /* TODO: also get wm_normal_hints here. implement after we got rid of xcb-event */
 
     geomc = xcb_get_geometry(conn, d);
 
@@ -126,6 +117,18 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
         goto out;
     }
 
+#define GET_PROPERTY(atom, len) xcb_get_property_unchecked(conn, false, window, atom, XCB_GET_PROPERTY_TYPE_ANY, 0, len)
+
+    wm_type_cookie = GET_PROPERTY(A__NET_WM_WINDOW_TYPE, UINT32_MAX);
+    strut_cookie = GET_PROPERTY(A__NET_WM_STRUT_PARTIAL, UINT32_MAX);
+    state_cookie = GET_PROPERTY(A__NET_WM_STATE, UINT32_MAX);
+    utf8_title_cookie = GET_PROPERTY(A__NET_WM_NAME, 128);
+    leader_cookie = GET_PROPERTY(A_WM_CLIENT_LEADER, UINT32_MAX);
+    transient_cookie = GET_PROPERTY(A_WM_TRANSIENT_FOR, UINT32_MAX);
+    title_cookie = GET_PROPERTY(A_WM_NAME, 128);
+    class_cookie = GET_PROPERTY(A_WM_CLASS, 128);
+    /* TODO: also get wm_normal_hints here. implement after we got rid of xcb-event */
+
     DLOG("reparenting!\n");
     uint32_t mask = 0;
     uint32_t values[1];
@@ -157,7 +160,7 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
     Con *search_at = croot;
 
     xcb_get_property_reply_t *reply = xcb_get_property_reply(conn, wm_type_cookie, NULL);
-    if (xcb_reply_contains_atom(reply, atoms[_NET_WM_WINDOW_TYPE_DOCK])) {
+    if (xcb_reply_contains_atom(reply, A__NET_WM_WINDOW_TYPE_DOCK)) {
         LOG("This window is of type dock\n");
         Output *output = get_output_containing(geom->x, geom->y);
         if (output != NULL) {
@@ -254,10 +257,10 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
 
     /* set floating if necessary */
     bool want_floating = false;
-    if (xcb_reply_contains_atom(reply, atoms[_NET_WM_WINDOW_TYPE_DIALOG]) ||
-        xcb_reply_contains_atom(reply, atoms[_NET_WM_WINDOW_TYPE_UTILITY]) ||
-        xcb_reply_contains_atom(reply, atoms[_NET_WM_WINDOW_TYPE_TOOLBAR]) ||
-        xcb_reply_contains_atom(reply, atoms[_NET_WM_WINDOW_TYPE_SPLASH])) {
+    if (xcb_reply_contains_atom(reply, A__NET_WM_WINDOW_TYPE_DIALOG) ||
+        xcb_reply_contains_atom(reply, A__NET_WM_WINDOW_TYPE_UTILITY) ||
+        xcb_reply_contains_atom(reply, A__NET_WM_WINDOW_TYPE_TOOLBAR) ||
+        xcb_reply_contains_atom(reply, A__NET_WM_WINDOW_TYPE_SPLASH)) {
         LOG("This window is a dialog window, setting floating\n");
         want_floating = true;
     }
@@ -308,7 +311,7 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki
     xcb_change_window_attributes(conn, window, mask, values);
 
     reply = xcb_get_property_reply(conn, state_cookie, NULL);
-    if (xcb_reply_contains_atom(reply, atoms[_NET_WM_STATE_FULLSCREEN]))
+    if (xcb_reply_contains_atom(reply, A__NET_WM_STATE_FULLSCREEN))
         con_toggle_fullscreen(nc);
 
     /* Put the client inside the save set. Upon termination (whether killed or
index d6128b5b82a23228ec24dd4058e213ed41aa77c1..1d3e4ab719979832be0066b2314509e2aa3ec58b 100644 (file)
 
 #include <X11/keysym.h>
 
-#include "i3.h"
-#include "util.h"
-#include "xcb.h"
-#include "log.h"
-#include "config.h"
-#include "randr.h"
+#include "all.h"
 
 static xcb_gcontext_t pixmap_gc;
 static xcb_pixmap_t pixmap;
@@ -159,12 +154,6 @@ void handle_signal(int sig, siginfo_t *info, void *data) {
     sigaction(sig, &action, NULL);
     raised_signal = sig;
 
-    /* setup event handler for key presses */
-    xcb_event_handlers_t sig_evenths;
-    memset(&sig_evenths, 0, sizeof(xcb_event_handlers_t));
-    xcb_event_handlers_init(conn, &sig_evenths);
-    xcb_event_set_key_press_handler(&sig_evenths, sig_handle_key_press, NULL);
-
     /* width and height of the popup window, so that the text fits in */
     int crash_text_num = sizeof(crash_text) / sizeof(char*);
     int height = 13 + (crash_text_num * config.font.height);
@@ -203,7 +192,16 @@ void handle_signal(int sig, siginfo_t *info, void *data) {
         xcb_flush(conn);
     }
 
-    xcb_event_wait_for_event_loop(&sig_evenths);
+    xcb_generic_event_t *event;
+    /* Yay, more own eventhandlers… */
+    while ((event = xcb_wait_for_event(conn))) {
+        /* Strip off the highest bit (set if the event is generated) */
+        int type = (event->response_type & 0x7F);
+        if (type == XCB_KEY_PRESS) {
+            sig_handle_key_press(NULL, conn, (xcb_key_press_event_t*)event);
+        }
+        free(event);
+    }
 }
 
 /*
index 11be7c6f01b5b76cbc9bd379a7852bd53e980ff4..ffc73cd0160eeb1c97e5236234d0c7328eb76787 100644 (file)
@@ -136,7 +136,7 @@ void window_update_transient_for(i3Window *win, xcb_get_property_reply_t *prop)
     }
 
     xcb_window_t transient_for;
-    if (!xcb_get_wm_transient_for_from_reply(&transient_for, prop))
+    if (!xcb_icccm_get_wm_transient_for_from_reply(&transient_for, prop))
         return;
 
     DLOG("Transient for changed to %08x\n", transient_for);
diff --git a/src/x.c b/src/x.c
index 7a3385e5b86d14e8ea5d06f83fafb07d01960012..374fd1626ca12073d0f191d014c71a9f563e46d6 100644 (file)
--- a/src/x.c
+++ b/src/x.c
@@ -180,11 +180,11 @@ void x_con_kill(Con *con) {
  */
 static bool window_supports_protocol(xcb_window_t window, xcb_atom_t atom) {
     xcb_get_property_cookie_t cookie;
-    xcb_get_wm_protocols_reply_t protocols;
+    xcb_icccm_get_wm_protocols_reply_t protocols;
     bool result = false;
 
-    cookie = xcb_get_wm_protocols_unchecked(conn, window, atoms[WM_PROTOCOLS]);
-    if (xcb_get_wm_protocols_reply(conn, cookie, &protocols, NULL) != 1)
+    cookie = xcb_icccm_get_wm_protocols_unchecked(conn, window, A_WM_PROTOCOLS);
+    if (xcb_icccm_get_wm_protocols_reply(conn, cookie, &protocols, NULL) != 1)
         return false;
 
     /* Check if the client’s protocols have the requested atom set */
@@ -192,7 +192,7 @@ static bool window_supports_protocol(xcb_window_t window, xcb_atom_t atom) {
         if (protocols.atoms[i] == atom)
             result = true;
 
-    xcb_get_wm_protocols_reply_wipe(&protocols);
+    xcb_icccm_get_wm_protocols_reply_wipe(&protocols);
 
     return result;
 }
@@ -203,7 +203,7 @@ static bool window_supports_protocol(xcb_window_t window, xcb_atom_t atom) {
  */
 void x_window_kill(xcb_window_t window) {
     /* if this window does not support WM_DELETE_WINDOW, we kill it the hard way */
-    if (!window_supports_protocol(window, atoms[WM_DELETE_WINDOW])) {
+    if (!window_supports_protocol(window, A_WM_DELETE_WINDOW)) {
         LOG("Killing window the hard way\n");
         xcb_kill_client(conn, window);
         return;
@@ -215,9 +215,9 @@ void x_window_kill(xcb_window_t window) {
 
     ev.response_type = XCB_CLIENT_MESSAGE;
     ev.window = window;
-    ev.type = atoms[WM_PROTOCOLS];
+    ev.type = A_WM_PROTOCOLS;
     ev.format = 32;
-    ev.data.data32[0] = atoms[WM_DELETE_WINDOW];
+    ev.data.data32[0] = A_WM_DELETE_WINDOW;
     ev.data.data32[1] = XCB_CURRENT_TIME;
 
     LOG("Sending WM_DELETE to the client\n");
@@ -389,7 +389,7 @@ static void x_push_node(Con *con) {
         DLOG("pushing name %s for con %p\n", state->name, con);
 
         xcb_change_property(conn, XCB_PROP_MODE_REPLACE, con->frame,
-                            WM_NAME, STRING, 8, strlen(state->name), state->name);
+                            A_WM_NAME, A_STRING, 8, strlen(state->name), state->name);
         FREE(state->name);
     }
 
@@ -468,9 +468,9 @@ static void x_push_node(Con *con) {
         if (con->window != NULL) {
             /* Set WM_STATE_NORMAL because GTK applications don’t want to
              * drag & drop if we don’t. Also, xprop(1) needs it. */
-            long data[] = { XCB_WM_STATE_NORMAL, XCB_NONE };
+            long data[] = { XCB_ICCCM_WM_STATE_NORMAL, XCB_NONE };
             xcb_change_property(conn, XCB_PROP_MODE_REPLACE, con->window->id,
-                                atoms[WM_STATE], atoms[WM_STATE], 32, 2, data);
+                                A_WM_STATE, A_WM_STATE, 32, 2, data);
         }
 
         if (!state->child_mapped && con->window != NULL) {
@@ -528,9 +528,9 @@ static void x_push_node_unmaps(Con *con) {
         xcb_void_cookie_t cookie;
         if (con->window != NULL) {
             /* Set WM_STATE_WITHDRAWN, it seems like Java apps need it */
-            long data[] = { XCB_WM_STATE_WITHDRAWN, XCB_NONE };
+            long data[] = { XCB_ICCCM_WM_STATE_WITHDRAWN, XCB_NONE };
             xcb_change_property(conn, XCB_PROP_MODE_REPLACE, con->window->id,
-                                atoms[WM_STATE], atoms[WM_STATE], 32, 2, data);
+                                A_WM_STATE, A_WM_STATE, 32, 2, data);
         }
 
         cookie = xcb_unmap_window(conn, con->frame);
@@ -624,9 +624,9 @@ void x_push_changes(Con *con) {
 
             ev.response_type = XCB_CLIENT_MESSAGE;
             ev.window = to_focus;
-            ev.type = atoms[WM_PROTOCOLS];
+            ev.type = A_WM_PROTOCOLS;
             ev.format = 32;
-            ev.data.data32[0] = atoms[WM_TAKE_FOCUS];
+            ev.data.data32[0] = A_WM_TAKE_FOCUS;
             ev.data.data32[1] = XCB_CURRENT_TIME;
 
             DLOG("Sending WM_TAKE_FOCUS to the client\n");