1// Copyright (C) 2018 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3#ifndef QXCBBASICCONNECTION_H
4#define QXCBBASICCONNECTION_H
5
6#include "qxcbatom.h"
7#include "qxcbexport.h"
8
9#include <QtCore/QPair>
10#include <QtCore/QObject>
11#include <QtCore/QByteArray>
12#include <QtCore/QLoggingCategory>
13#include <QtGui/private/qtguiglobal_p.h>
14
15#include <xcb/xcb.h>
16
17#include <memory>
18
19QT_BEGIN_NAMESPACE
20
21Q_DECLARE_LOGGING_CATEGORY(lcQpaXcb)
22
23class Q_XCB_EXPORT QXcbBasicConnection : public QObject
24{
25 Q_OBJECT
26public:
27 QXcbBasicConnection(const char *displayName);
28 ~QXcbBasicConnection();
29
30#if QT_CONFIG(xcb_xlib)
31 void *xlib_display() const { return m_xlibDisplay; }
32#endif
33 const char *displayName() const { return m_displayName.constData(); }
34 int primaryScreenNumber() const { return m_primaryScreenNumber; }
35 xcb_connection_t *xcb_connection() const { return m_xcbConnection; }
36 bool isConnected() const {
37 return m_xcbConnection && !xcb_connection_has_error(c: m_xcbConnection);
38 }
39 const xcb_setup_t *setup() const { return m_setup; }
40
41 size_t maxRequestDataBytes(size_t requestSize) const;
42
43 inline xcb_atom_t atom(QXcbAtom::Atom qatom) const { return m_xcbAtom.atom(atom: qatom); }
44 QXcbAtom::Atom qatom(xcb_atom_t atom) const { return m_xcbAtom.qatom(atom); }
45 xcb_atom_t internAtom(const char *name);
46 QByteArray atomName(xcb_atom_t atom);
47
48 bool hasXFixes() const { return m_hasXFixes; }
49 bool hasXShape() const { return m_hasXhape; }
50 bool hasXRandr() const { return m_hasXRandr; }
51 bool hasInputShape() const { return m_hasInputShape; }
52 bool hasXKB() const { return m_hasXkb; }
53 bool hasXRender(int major = -1, int minor = -1) const {
54 if (m_hasXRender && major != -1 && minor != -1)
55 return m_xrenderVersion >= qMakePair(value1&: major, value2&: minor);
56
57 return m_hasXRender;
58 }
59 bool hasXInput2() const { return m_xi2Enabled; }
60 bool hasShm() const { return m_hasShm; }
61 bool hasShmFd() const { return m_hasShmFd; }
62 bool hasXSync() const { return m_hasXSync; }
63 bool hasBigRequest() const;
64
65 bool isAtLeastXRandR12() const { return m_hasXRandr && m_xrandr1Minor >= 2; }
66 bool isAtLeastXRandR15() const { return m_hasXRandr && m_xrandr1Minor >= 5; }
67
68 bool isAtLeastXI21() const { return m_xi2Enabled && m_xi2Minor >= 1; }
69 bool isAtLeastXI22() const { return m_xi2Enabled && m_xi2Minor >= 2; }
70 bool isAtLeastXI24() const { return m_xi2Enabled && m_xi2Minor >= 4; }
71 bool isXIEvent(xcb_generic_event_t *event) const;
72 bool isXIType(xcb_generic_event_t *event, uint16_t type) const;
73
74 bool isXFixesType(uint responseType, int eventType) const;
75 bool isXRandrType(uint responseType, int eventType) const;
76 bool isXkbType(uint responseType) const; // https://bugs.freedesktop.org/show_bug.cgi?id=51295
77
78protected:
79 void initializeShm();
80 void initializeXFixes();
81 void initializeXRender();
82 void initializeXRandr();
83 void initializeXShape();
84 void initializeXKB();
85 void initializeXSync();
86 void initializeXInput2();
87
88private:
89#if QT_CONFIG(xcb_xlib)
90 void *m_xlibDisplay = nullptr;
91#endif
92 QByteArray m_displayName;
93 xcb_connection_t *m_xcbConnection = nullptr;
94 int m_primaryScreenNumber = 0;
95 const xcb_setup_t *m_setup = nullptr;
96 QXcbAtom m_xcbAtom;
97
98 bool m_hasXFixes = false;
99 bool m_hasXhape = false;
100 bool m_hasInputShape;
101 bool m_hasXRandr = false;
102 bool m_hasXkb = false;
103 bool m_hasXRender = false;
104 bool m_hasShm = false;
105 bool m_hasShmFd = false;
106 bool m_hasXSync = false;
107
108 QPair<int, int> m_xrenderVersion;
109
110 bool m_xi2Enabled = false;
111 int m_xi2Minor = -1;
112 int m_xiOpCode = -1;
113 uint32_t m_xinputFirstEvent = 0;
114
115 int m_xrandr1Minor = -1;
116
117 uint32_t m_xfixesFirstEvent = 0;
118 uint32_t m_xrandrFirstEvent = 0;
119 uint32_t m_xkbFirstEvent = 0;
120
121 uint32_t m_maximumRequestLength = 0;
122};
123
124#define Q_XCB_REPLY_CONNECTION_ARG(connection, ...) connection
125
126struct QStdFreeDeleter {
127 void operator()(void *p) const noexcept { return std::free(ptr: p); }
128};
129
130#define Q_XCB_REPLY(call, ...) \
131 std::unique_ptr<call##_reply_t, QStdFreeDeleter>( \
132 call##_reply(Q_XCB_REPLY_CONNECTION_ARG(__VA_ARGS__), call(__VA_ARGS__), nullptr) \
133 )
134
135#define Q_XCB_REPLY_UNCHECKED(call, ...) \
136 std::unique_ptr<call##_reply_t, QStdFreeDeleter>( \
137 call##_reply(Q_XCB_REPLY_CONNECTION_ARG(__VA_ARGS__), call##_unchecked(__VA_ARGS__), nullptr) \
138 )
139
140QT_END_NAMESPACE
141
142#endif // QXCBBASICCONNECTION_H
143

source code of qtbase/src/plugins/platforms/xcb/qxcbconnection_basic.h