diff --git a/plugins/platforms/x11/standalone/xinputintegration.cpp b/plugins/platforms/x11/standalone/xinputintegration.cpp index 66ec1d84d4..32250708fa 100644 --- a/plugins/platforms/x11/standalone/xinputintegration.cpp +++ b/plugins/platforms/x11/standalone/xinputintegration.cpp @@ -43,6 +43,32 @@ static inline qreal fixed1616ToReal(FP1616 val) return (val) * 1.0 / (1 << 16); } +class GeEventMemMover +{ +public: + GeEventMemMover(xcb_generic_event_t *event) + : m_event(reinterpret_cast(event)) + { + // xcb event structs contain stuff that wasn't on the wire, the full_sequence field + // adds an extra 4 bytes and generic events cookie data is on the wire right after the standard 32 bytes. + // Move this data back to have the same layout in memory as it was on the wire + // and allow casting, overwriting the full_sequence field. + memmove((char*) m_event + 32, (char*) m_event + 36, m_event->length * 4); + } + ~GeEventMemMover() + { + // move memory layout back, so that Qt can do the same without breaking + memmove((char*) m_event + 36, (char *) m_event + 32, m_event->length * 4); + } + + xcb_ge_generic_event_t *operator->() const { + return m_event; + } + +private: + xcb_ge_generic_event_t *m_event; +}; + class XInputEventFilter : public X11EventFilter { public: @@ -52,8 +78,7 @@ public: virtual ~XInputEventFilter() = default; bool event(xcb_generic_event_t *event) override { - xcb_ge_generic_event_t *ge = reinterpret_cast(event); - xi2PrepareXIGenericDeviceEvent(ge); + GeEventMemMover ge(event); switch (ge->event_type) { case XI_RawKeyPress: { auto re = reinterpret_cast(event); @@ -118,7 +143,7 @@ public: } break; case XI_TouchBegin: { - auto e = reinterpret_cast(ge); + auto e = reinterpret_cast(event); m_lastTouchPositions.insert(e->detail, QPointF(fixed1616ToReal(e->event_x), fixed1616ToReal(e->event_y))); break; } @@ -175,14 +200,6 @@ private: return m_x11Display; } - void xi2PrepareXIGenericDeviceEvent(xcb_ge_generic_event_t *event) { - // xcb event structs contain stuff that wasn't on the wire, the full_sequence field - // adds an extra 4 bytes and generic events cookie data is on the wire right after the standard 32 bytes. - // Move this data back to have the same layout in memory as it was on the wire - // and allow casting, overwriting the full_sequence field. - memmove((char*) event + 32, (char*) event + 36, event->length * 4); - } - QPointer m_x11Cursor; Display *m_x11Display = nullptr; uint32_t m_trackingTouchId = 0;