From 2d5541d6c30c67d6a469cba372b6e336a2eeb626 Mon Sep 17 00:00:00 2001 From: Povilas Kanapickas Date: Fri, 3 Sep 2021 16:23:06 +0300 Subject: [PATCH] 3rdparty: Fix forwards-compatibility bug in bundled xinput xcb module libxcb thinks that it knows about all device class types sent by the X server XInput extension. With the addition of touchpad gestures in XInput 2.4 and X server 21.1 this is no longer the case and libxcb fails horribly by thinking that the protocol was malformed. The X server currently has a workaround, but it would not address the following situation: - there are multiple modules within the same X client (e.g. part of the application uses Qt, another part talks to X server via another library) - both of the modules talk to XI - at least one module requests for XI 2.4 protocol support. The request for XI 2.4 disables the workaround on the X server and Qt side would crash horribly. This bug is being fixed upstream in these MRs: https://gitlab.freedesktop.org/xorg/proto/xcbproto/-/merge_requests/23 https://gitlab.freedesktop.org/xorg/lib/libxcb/-/merge_requests/20 Change-Id: Idf345271340031152b512ef59f619313be5ec226 Reviewed-by: Allan Sandfeld Jensen Reviewed-by: Shawn Rutledge --- src/3rdparty/xcb/README | 24 ++++++++++++ .../libxcb/xinput-device-class-sizeof.patch | 38 +++++++++++++++++++ src/3rdparty/xcb/libxcb/xinput.c | 26 +------------ 3 files changed, 63 insertions(+), 25 deletions(-) create mode 100644 src/3rdparty/xcb/libxcb/xinput-device-class-sizeof.patch diff --git a/src/3rdparty/xcb/README b/src/3rdparty/xcb/README index 362fa54bf8..a97d883867 100644 --- a/src/3rdparty/xcb/README +++ b/src/3rdparty/xcb/README @@ -20,3 +20,27 @@ The xcb-xinput files where modified to use system includes, see: src/3rdparty/xcb/include/xcb/fixup-xinput-h.patch src/3rdparty/xcb/libxcb/fixup-xinput-c.patch +***************************************************************** + +Additionally, a forwards compatibility bug in libxcb xinput has been addressed +by the following patch: + +src/3rdparty/xcb/libxcb/xinput-device-class-sizeof.patch + +The crux of the issue is that libxcb thinks that it knows about all device +class types sent by the X server XInput extension. With the addition of +touchpad gestures in XInput 2.4 and X server 21.1 this is no longer the case +and libxcb fails horribly by thinking that the protocol was malformed. + +The X server currently has a workaround, but it would not address the following +situation: + + - there are multiple modules within the same X client (e.g. part of the application + uses Qt, another part talks to X server via another library) + - both of the modules talk to XI + - at least one module requests for XI 2.4 protocol support. + +The request for XI 2.4 disables the workaround on the X server and Qt side would +crash horribly. + +For more details, see https://gitlab.freedesktop.org/xorg/lib/libxcb/-/merge_requests/20 diff --git a/src/3rdparty/xcb/libxcb/xinput-device-class-sizeof.patch b/src/3rdparty/xcb/libxcb/xinput-device-class-sizeof.patch new file mode 100644 index 0000000000..2eacd7f3d2 --- /dev/null +++ b/src/3rdparty/xcb/libxcb/xinput-device-class-sizeof.patch @@ -0,0 +1,38 @@ +diff --git a/src/3rdparty/xcb/libxcb/xinput.c b/src/3rdparty/xcb/libxcb/xinput.c +index d4e3c250bc..5113213a61 100644 +--- a/src/3rdparty/xcb/libxcb/xinput.c ++++ b/src/3rdparty/xcb/libxcb/xinput.c +@@ -10535,32 +10535,8 @@ xcb_input_device_class_data_sizeof (const void *_buffer, + int + xcb_input_device_class_sizeof (const void *_buffer) + { +- char *xcb_tmp = (char *)_buffer; + const xcb_input_device_class_t *_aux = (xcb_input_device_class_t *)_buffer; +- unsigned int xcb_buffer_len = 0; +- unsigned int xcb_block_len = 0; +- unsigned int xcb_pad = 0; +- unsigned int xcb_align_to = 0; +- +- +- xcb_block_len += sizeof(xcb_input_device_class_t); +- xcb_tmp += xcb_block_len; +- xcb_buffer_len += xcb_block_len; +- xcb_block_len = 0; +- /* data */ +- xcb_block_len += xcb_input_device_class_data_sizeof(xcb_tmp, _aux->type); +- xcb_tmp += xcb_block_len; +- xcb_align_to = ALIGNOF(char); +- /* insert padding */ +- xcb_pad = -xcb_block_len & (xcb_align_to - 1); +- xcb_buffer_len += xcb_block_len + xcb_pad; +- if (0 != xcb_pad) { +- xcb_tmp += xcb_pad; +- xcb_pad = 0; +- } +- xcb_block_len = 0; +- +- return xcb_buffer_len; ++ return (_aux->len * 4); + } + + void * diff --git a/src/3rdparty/xcb/libxcb/xinput.c b/src/3rdparty/xcb/libxcb/xinput.c index d4e3c250bc..5113213a61 100644 --- a/src/3rdparty/xcb/libxcb/xinput.c +++ b/src/3rdparty/xcb/libxcb/xinput.c @@ -10535,32 +10535,8 @@ xcb_input_device_class_data_sizeof (const void *_buffer, int xcb_input_device_class_sizeof (const void *_buffer) { - char *xcb_tmp = (char *)_buffer; const xcb_input_device_class_t *_aux = (xcb_input_device_class_t *)_buffer; - unsigned int xcb_buffer_len = 0; - unsigned int xcb_block_len = 0; - unsigned int xcb_pad = 0; - unsigned int xcb_align_to = 0; - - - xcb_block_len += sizeof(xcb_input_device_class_t); - xcb_tmp += xcb_block_len; - xcb_buffer_len += xcb_block_len; - xcb_block_len = 0; - /* data */ - xcb_block_len += xcb_input_device_class_data_sizeof(xcb_tmp, _aux->type); - xcb_tmp += xcb_block_len; - xcb_align_to = ALIGNOF(char); - /* insert padding */ - xcb_pad = -xcb_block_len & (xcb_align_to - 1); - xcb_buffer_len += xcb_block_len + xcb_pad; - if (0 != xcb_pad) { - xcb_tmp += xcb_pad; - xcb_pad = 0; - } - xcb_block_len = 0; - - return xcb_buffer_len; + return (_aux->len * 4); } void *