Use xcb atoms properly
This commit is contained in:
		
							parent
							
								
									c986cc24a9
								
							
						
					
					
						commit
						902d6cc240
					
				| 
						 | 
					@ -15,7 +15,6 @@
 | 
				
			||||||
#include <wlr/render/gles2.h>
 | 
					#include <wlr/render/gles2.h>
 | 
				
			||||||
#include <wlr/util/log.h>
 | 
					#include <wlr/util/log.h>
 | 
				
			||||||
#include <X11/Xlib-xcb.h>
 | 
					#include <X11/Xlib-xcb.h>
 | 
				
			||||||
#include <xcb/glx.h>
 | 
					 | 
				
			||||||
#include <xcb/xcb.h>
 | 
					#include <xcb/xcb.h>
 | 
				
			||||||
#ifdef __linux__
 | 
					#ifdef __linux__
 | 
				
			||||||
#include <linux/input-event-codes.h>
 | 
					#include <linux/input-event-codes.h>
 | 
				
			||||||
| 
						 | 
					@ -25,6 +24,8 @@
 | 
				
			||||||
#include "backend/x11.h"
 | 
					#include "backend/x11.h"
 | 
				
			||||||
#include "util/signal.h"
 | 
					#include "util/signal.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define XCB_EVENT_RESPONSE_TYPE_MASK 0x7f
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static struct wlr_backend_impl backend_impl;
 | 
					static struct wlr_backend_impl backend_impl;
 | 
				
			||||||
static struct wlr_output_impl output_impl;
 | 
					static struct wlr_output_impl output_impl;
 | 
				
			||||||
static struct wlr_input_device_impl input_device_impl = { 0 };
 | 
					static struct wlr_input_device_impl input_device_impl = { 0 };
 | 
				
			||||||
| 
						 | 
					@ -44,7 +45,7 @@ static uint32_t xcb_button_to_wl(uint32_t button) {
 | 
				
			||||||
static bool handle_x11_event(struct wlr_x11_backend *x11, xcb_generic_event_t *event) {
 | 
					static bool handle_x11_event(struct wlr_x11_backend *x11, xcb_generic_event_t *event) {
 | 
				
			||||||
	struct wlr_x11_output *output = &x11->output;
 | 
						struct wlr_x11_output *output = &x11->output;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	switch (event->response_type) {
 | 
						switch (event->response_type & XCB_EVENT_RESPONSE_TYPE_MASK) {
 | 
				
			||||||
	case XCB_EXPOSE: {
 | 
						case XCB_EXPOSE: {
 | 
				
			||||||
		wlr_output_send_frame(&output->wlr_output);
 | 
							wlr_output_send_frame(&output->wlr_output);
 | 
				
			||||||
		break;
 | 
							break;
 | 
				
			||||||
| 
						 | 
					@ -144,9 +145,14 @@ static bool handle_x11_event(struct wlr_x11_backend *x11, xcb_generic_event_t *e
 | 
				
			||||||
		wlr_signal_emit_safe(&x11->pointer.events.motion_absolute, &abs);
 | 
							wlr_signal_emit_safe(&x11->pointer.events.motion_absolute, &abs);
 | 
				
			||||||
		break;
 | 
							break;
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	case XCB_GLX_DELETE_QUERIES_ARB: {
 | 
						case XCB_CLIENT_MESSAGE: {
 | 
				
			||||||
		wl_display_terminate(x11->wl_display);
 | 
							xcb_client_message_event_t *ev = (xcb_client_message_event_t *)event;
 | 
				
			||||||
		return true;
 | 
					
 | 
				
			||||||
 | 
							if (ev->data.data32[0] == x11->atoms.wm_delete_window) {
 | 
				
			||||||
 | 
								wl_display_terminate(x11->wl_display);
 | 
				
			||||||
 | 
								return true;
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		break;
 | 
							break;
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	default:
 | 
						default:
 | 
				
			||||||
| 
						 | 
					@ -181,13 +187,6 @@ static int signal_frame(void *data) {
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void init_atom(struct wlr_x11_backend *x11, struct wlr_x11_atom *atom,
 | 
					 | 
				
			||||||
		uint8_t only_if_exists, const char *name) {
 | 
					 | 
				
			||||||
	atom->cookie = xcb_intern_atom(x11->xcb_conn, only_if_exists, strlen(name),
 | 
					 | 
				
			||||||
		name);
 | 
					 | 
				
			||||||
	atom->reply = xcb_intern_atom_reply(x11->xcb_conn, atom->cookie, NULL);
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
static void parse_xcb_setup(struct wlr_output *output, xcb_connection_t *xcb_conn) {
 | 
					static void parse_xcb_setup(struct wlr_output *output, xcb_connection_t *xcb_conn) {
 | 
				
			||||||
	const xcb_setup_t *xcb_setup = xcb_get_setup(xcb_conn);
 | 
						const xcb_setup_t *xcb_setup = xcb_get_setup(xcb_conn);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -231,20 +230,54 @@ static bool wlr_x11_backend_start(struct wlr_backend *backend) {
 | 
				
			||||||
		return false;
 | 
							return false;
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	init_atom(x11, &x11->atoms.wm_protocols, 1, "WM_PROTOCOLS");
 | 
						struct {
 | 
				
			||||||
	init_atom(x11, &x11->atoms.wm_delete_window, 0, "WM_DELETE_WINDOW");
 | 
							const char *name;
 | 
				
			||||||
	init_atom(x11, &x11->atoms.net_wm_name, 1, "_NET_WM_NAME");
 | 
							xcb_intern_atom_cookie_t cookie;
 | 
				
			||||||
	init_atom(x11, &x11->atoms.utf8_string, 0, "UTF8_STRING");
 | 
							xcb_atom_t *atom;
 | 
				
			||||||
 | 
						} atom[] = {
 | 
				
			||||||
 | 
							{
 | 
				
			||||||
 | 
								.name = "WM_PROTOCOLS",
 | 
				
			||||||
 | 
								.atom = &x11->atoms.wm_protocols,
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
							{
 | 
				
			||||||
 | 
								.name = "WM_DELETE_WINDOW",
 | 
				
			||||||
 | 
								.atom = &x11->atoms.wm_delete_window,
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
							{
 | 
				
			||||||
 | 
								.name = "_NET_WM_NAME",
 | 
				
			||||||
 | 
								.atom = &x11->atoms.net_wm_name,
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
							{
 | 
				
			||||||
 | 
								.name = "UTF8_STRING",
 | 
				
			||||||
 | 
								.atom = &x11->atoms.utf8_string,
 | 
				
			||||||
 | 
							},
 | 
				
			||||||
 | 
						};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for (size_t i = 0; i < sizeof(atom) / sizeof(atom[0]); ++i) {
 | 
				
			||||||
 | 
							atom[i].cookie = xcb_intern_atom(x11->xcb_conn,
 | 
				
			||||||
 | 
								true, strlen(atom[i].name), atom[i].name);
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for (size_t i = 0; i < sizeof(atom) / sizeof(atom[0]); ++i) {
 | 
				
			||||||
 | 
							xcb_intern_atom_reply_t *reply = xcb_intern_atom_reply(
 | 
				
			||||||
 | 
								x11->xcb_conn, atom[i].cookie, NULL);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							if (reply) {
 | 
				
			||||||
 | 
								*atom[i].atom = reply->atom;
 | 
				
			||||||
 | 
								free(reply);
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								*atom[i].atom = XCB_ATOM_NONE;
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	xcb_change_property(x11->xcb_conn, XCB_PROP_MODE_REPLACE, output->win,
 | 
						xcb_change_property(x11->xcb_conn, XCB_PROP_MODE_REPLACE, output->win,
 | 
				
			||||||
		x11->atoms.wm_protocols.reply->atom, XCB_ATOM_ATOM, 32, 1,
 | 
							x11->atoms.wm_protocols, XCB_ATOM_ATOM, 32, 1,
 | 
				
			||||||
		&x11->atoms.wm_delete_window.reply->atom);
 | 
							&x11->atoms.wm_delete_window);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	char title[32];
 | 
						char title[32];
 | 
				
			||||||
	if (snprintf(title, sizeof(title), "wlroots - %s", output->wlr_output.name)) {
 | 
						if (snprintf(title, sizeof(title), "wlroots - %s", output->wlr_output.name)) {
 | 
				
			||||||
		xcb_change_property(x11->xcb_conn, XCB_PROP_MODE_REPLACE, output->win,
 | 
							xcb_change_property(x11->xcb_conn, XCB_PROP_MODE_REPLACE, output->win,
 | 
				
			||||||
			x11->atoms.net_wm_name.reply->atom,
 | 
								x11->atoms.net_wm_name, x11->atoms.utf8_string, 8,
 | 
				
			||||||
			x11->atoms.utf8_string.reply->atom, 8,
 | 
					 | 
				
			||||||
			strlen(title), title);
 | 
								strlen(title), title);
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -17,11 +17,6 @@ struct wlr_x11_output {
 | 
				
			||||||
	EGLSurface surf;
 | 
						EGLSurface surf;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct wlr_x11_atom {
 | 
					 | 
				
			||||||
	xcb_intern_atom_cookie_t cookie;
 | 
					 | 
				
			||||||
	xcb_intern_atom_reply_t *reply;
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
struct wlr_x11_backend {
 | 
					struct wlr_x11_backend {
 | 
				
			||||||
	struct wlr_backend backend;
 | 
						struct wlr_backend backend;
 | 
				
			||||||
	struct wl_display *wl_display;
 | 
						struct wl_display *wl_display;
 | 
				
			||||||
| 
						 | 
					@ -44,10 +39,10 @@ struct wlr_x11_backend {
 | 
				
			||||||
	struct wl_event_source *frame_timer;
 | 
						struct wl_event_source *frame_timer;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	struct {
 | 
						struct {
 | 
				
			||||||
		struct wlr_x11_atom wm_protocols;
 | 
							xcb_atom_t wm_protocols;
 | 
				
			||||||
		struct wlr_x11_atom wm_delete_window;
 | 
							xcb_atom_t wm_delete_window;
 | 
				
			||||||
		struct wlr_x11_atom net_wm_name;
 | 
							xcb_atom_t net_wm_name;
 | 
				
			||||||
		struct wlr_x11_atom utf8_string;
 | 
							xcb_atom_t utf8_string;
 | 
				
			||||||
	} atoms;
 | 
						} atoms;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	// The time we last received an event
 | 
						// The time we last received an event
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue