diff --git a/hw/xnest/meson.build b/hw/xnest/meson.build index 3144134d9..d3a3e6900 100644 --- a/hw/xnest/meson.build +++ b/hw/xnest/meson.build @@ -18,6 +18,7 @@ srcs = [ '../../mi/miinitext.c', '../../mi/miinitext.h', 'xcb.c', + 'xkb.c', ] x11_xcb_dep = dependency('x11-xcb', required: true) diff --git a/hw/xnest/xcb.c b/hw/xnest/xcb.c index c2170b5d3..38675db80 100644 --- a/hw/xnest/xcb.c +++ b/hw/xnest/xcb.c @@ -18,6 +18,7 @@ #include "Xnest.h" #include "xnest-xcb.h" +#include "xnest-xkb.h" #include "XNGC.h" #include "Display.h" @@ -219,7 +220,7 @@ int xnest_xkb_device_id(xcb_connection_t *conn) xcb_xkb_get_kbd_by_name_reply_t *reply = xcb_xkb_get_kbd_by_name_reply( xnestUpstreamInfo.conn, - xcb_xkb_get_kbd_by_name( + xcb_xkb_get_kbd_by_name_2( xnestUpstreamInfo.conn, XCB_XKB_ID_USE_CORE_KBD, XkbGBN_AllComponentsMask_2, diff --git a/hw/xnest/xkb.c b/hw/xnest/xkb.c new file mode 100644 index 000000000..8d5166848 --- /dev/null +++ b/hw/xnest/xkb.c @@ -0,0 +1,90 @@ +#include +#include +#include +#include /* for offsetof() */ + +#include +#include +#include + +#include "xnest-xkb.h" + +xcb_xkb_get_kbd_by_name_cookie_t +xcb_xkb_get_kbd_by_name_2 (xcb_connection_t *c, + xcb_xkb_device_spec_t deviceSpec, + uint16_t need, + uint16_t want, + uint8_t load, + uint32_t data_len, + const uint8_t *data) +{ + static const xcb_protocol_request_t xcb_req = { + .count = 4, + .ext = &xcb_xkb_id, + .opcode = XCB_XKB_GET_KBD_BY_NAME, + .isvoid = 0 + }; + + struct iovec xcb_parts[6]; + xcb_xkb_get_kbd_by_name_cookie_t xcb_ret; + xcb_xkb_get_kbd_by_name_request_t xcb_out; + + xcb_out.deviceSpec = deviceSpec; + xcb_out.need = need; + xcb_out.want = want; + xcb_out.load = load; + xcb_out.pad0 = 0; + + xcb_parts[2].iov_base = (char *) &xcb_out; + xcb_parts[2].iov_len = sizeof(xcb_out); + xcb_parts[3].iov_base = 0; + xcb_parts[3].iov_len = -xcb_parts[2].iov_len & 3; + /* uint8_t data */ + xcb_parts[4].iov_base = (char *) data; + xcb_parts[4].iov_len = data_len * sizeof(uint8_t); + xcb_parts[5].iov_base = 0; + xcb_parts[5].iov_len = -xcb_parts[4].iov_len & 3; + + xcb_ret.sequence = xcb_send_request(c, XCB_REQUEST_CHECKED, xcb_parts + 2, &xcb_req); + return xcb_ret; +} + +xcb_xkb_get_kbd_by_name_cookie_t +xcb_xkb_get_kbd_by_name_2_unchecked (xcb_connection_t *c, + xcb_xkb_device_spec_t deviceSpec, + uint16_t need, + uint16_t want, + uint8_t load, + uint32_t data_len, + const uint8_t *data) +{ + static const xcb_protocol_request_t xcb_req = { + .count = 4, + .ext = &xcb_xkb_id, + .opcode = XCB_XKB_GET_KBD_BY_NAME, + .isvoid = 0 + }; + + struct iovec xcb_parts[6]; + xcb_xkb_get_kbd_by_name_cookie_t xcb_ret; + xcb_xkb_get_kbd_by_name_request_t xcb_out; + + xcb_out.deviceSpec = deviceSpec; + xcb_out.need = need; + xcb_out.want = want; + xcb_out.load = load; + xcb_out.pad0 = 0; + + xcb_parts[2].iov_base = (char *) &xcb_out; + xcb_parts[2].iov_len = sizeof(xcb_out); + xcb_parts[3].iov_base = 0; + xcb_parts[3].iov_len = -xcb_parts[2].iov_len & 3; + /* uint8_t data */ + xcb_parts[4].iov_base = (char *) data; + xcb_parts[4].iov_len = data_len * sizeof(uint8_t); + xcb_parts[5].iov_base = 0; + xcb_parts[5].iov_len = -xcb_parts[4].iov_len & 3; + + xcb_ret.sequence = xcb_send_request(c, 0, xcb_parts + 2, &xcb_req); + return xcb_ret; +} diff --git a/hw/xnest/xnest-xkb.h b/hw/xnest/xnest-xkb.h new file mode 100644 index 000000000..d2c820a04 --- /dev/null +++ b/hw/xnest/xnest-xkb.h @@ -0,0 +1,29 @@ +/* SPDX-License-Identifier: MIT OR X11 + * + * Copyright © 2024 Enrico Weigelt, metux IT consult + */ +#ifndef __XNEST__XKB_H +#define __XNEST__XKB_H + +#include +#include + +xcb_xkb_get_kbd_by_name_cookie_t +xcb_xkb_get_kbd_by_name_2 (xcb_connection_t *c, + xcb_xkb_device_spec_t deviceSpec, + uint16_t need, + uint16_t want, + uint8_t load, + uint32_t data_len, + const uint8_t *data); + +xcb_xkb_get_kbd_by_name_cookie_t +xcb_xkb_get_kbd_by_name_2_unchecked (xcb_connection_t *c, + xcb_xkb_device_spec_t deviceSpec, + uint16_t need, + uint16_t want, + uint8_t load, + uint32_t data_len, + const uint8_t *data); + +#endif /* __XNEST__XKB_H */