diff options
author | Samuel Rødal <samuel.rodal@digia.com> | 2012-11-02 15:08:25 +0100 |
---|---|---|
committer | The Qt Project <gerrit-noreply@qt-project.org> | 2012-11-07 08:42:29 +0100 |
commit | 04f6edc37947dee62bf735e39aa5ae9cf5a637c7 (patch) | |
tree | e00bb11596246af2765ac9726db92e2ac1b69426 /src | |
parent | 565b6bd6354f9edd63e493aa41087550b4e08ae5 (diff) |
Resolve xcb_poll_for_queued_event at run-time.
By not making this a compile time decision we ensure forward
compatibility for older xcb versions if the xcb plugin is built against
a newer xcb.
Change-Id: I744777d53bf7b8deb6eff372494f4403d19d364c
Reviewed-by: Kai Koehne <kai.koehne@digia.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.cpp | 62 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.h | 12 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/xcb.pro | 4 |
3 files changed, 49 insertions, 29 deletions
diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp index e35954caf9..266491d5d9 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection.cpp @@ -58,6 +58,7 @@ #include <QTimer> #include <QByteArray> +#include <dlfcn.h> #include <stdio.h> #include <errno.h> #include <xcb/shm.h> @@ -281,18 +282,16 @@ QXcbConnection::QXcbConnection(QXcbNativeInterface *nativeInterface, const char qFatal("QXcbConnection: Could not connect to display %s", m_displayName.constData()); m_reader = new QXcbEventReader(this); -#ifdef XCB_POLL_FOR_QUEUED_EVENT connect(m_reader, SIGNAL(eventPending()), this, SLOT(processXcbEvents()), Qt::QueuedConnection); connect(m_reader, SIGNAL(finished()), this, SLOT(processXcbEvents())); - m_reader->start(); -#else - QSocketNotifier *notifier = new QSocketNotifier(xcb_get_file_descriptor(xcb_connection()), QSocketNotifier::Read, this); - connect(notifier, SIGNAL(activated(int)), this, SLOT(processXcbEvents())); + if (!m_reader->startThread()) { + QSocketNotifier *notifier = new QSocketNotifier(xcb_get_file_descriptor(xcb_connection()), QSocketNotifier::Read, this); + connect(notifier, SIGNAL(activated(int)), this, SLOT(processXcbEvents())); - QAbstractEventDispatcher *dispatcher = QGuiApplicationPrivate::eventDispatcher; - connect(dispatcher, SIGNAL(aboutToBlock()), this, SLOT(processXcbEvents())); - connect(dispatcher, SIGNAL(awake()), this, SLOT(processXcbEvents())); -#endif + QAbstractEventDispatcher *dispatcher = QGuiApplicationPrivate::eventDispatcher; + connect(dispatcher, SIGNAL(aboutToBlock()), this, SLOT(processXcbEvents())); + connect(dispatcher, SIGNAL(awake()), this, SLOT(processXcbEvents())); + } xcb_extension_t *extensions[] = { &xcb_shm_id, &xcb_xfixes_id, &xcb_randr_id, &xcb_shape_id, &xcb_sync_id, @@ -364,10 +363,11 @@ QXcbConnection::~QXcbConnection() finalizeXInput2(); #endif -#ifdef XCB_POLL_FOR_QUEUED_EVENT - sendConnectionEvent(QXcbAtom::_QT_CLOSE_CONNECTION); - m_reader->wait(); -#endif + if (m_reader->isRunning()) { + sendConnectionEvent(QXcbAtom::_QT_CLOSE_CONNECTION); + m_reader->wait(); + } + delete m_reader; #ifdef XCB_USE_EGL @@ -808,14 +808,37 @@ void QXcbConnection::addPeekFunc(PeekFunc f) m_peekFuncs.append(f); } -#ifdef XCB_POLL_FOR_QUEUED_EVENT +QXcbEventReader::QXcbEventReader(QXcbConnection *connection) + : m_connection(connection) + , m_xcb_poll_for_queued_event(0) +{ +#ifdef RTLD_DEFAULT + m_xcb_poll_for_queued_event = (XcbPollForQueuedEventFunctionPointer)dlsym(RTLD_DEFAULT, "xcb_poll_for_queued_event"); +#endif + +#ifdef Q_XCB_DEBUG + if (m_xcb_poll_for_queued_event) + qDebug("Using threaded event reader with xcb_poll_for_queued_event"); +#endif +} + +bool QXcbEventReader::startThread() +{ + if (m_xcb_poll_for_queued_event) { + QThread::start(); + return true; + } + + return false; +} + void QXcbEventReader::run() { xcb_generic_event_t *event; while (m_connection && (event = xcb_wait_for_event(m_connection->xcb_connection()))) { m_mutex.lock(); addEvent(event); - while (m_connection && (event = xcb_poll_for_queued_event(m_connection->xcb_connection()))) + while (m_connection && (event = m_xcb_poll_for_queued_event(m_connection->xcb_connection()))) addEvent(event); m_mutex.unlock(); emit eventPending(); @@ -824,7 +847,6 @@ void QXcbEventReader::run() for (int i = 0; i < m_events.size(); ++i) free(m_events.at(i)); } -#endif void QXcbEventReader::addEvent(xcb_generic_event_t *event) { @@ -837,10 +859,10 @@ void QXcbEventReader::addEvent(xcb_generic_event_t *event) QXcbEventArray *QXcbEventReader::lock() { m_mutex.lock(); -#ifndef XCB_POLL_FOR_QUEUED_EVENT - while (xcb_generic_event_t *event = xcb_poll_for_event(m_connection->xcb_connection())) - m_events << event; -#endif + if (!m_xcb_poll_for_queued_event) { + while (xcb_generic_event_t *event = xcb_poll_for_event(m_connection->xcb_connection())) + m_events << event; + } return &m_events; } diff --git a/src/plugins/platforms/xcb/qxcbconnection.h b/src/plugins/platforms/xcb/qxcbconnection.h index 8b2315c67e..f466928360 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.h +++ b/src/plugins/platforms/xcb/qxcbconnection.h @@ -278,18 +278,15 @@ class QXcbEventReader : public QThread { Q_OBJECT public: - QXcbEventReader(QXcbConnection *connection) - : m_connection(connection) - { - } + QXcbEventReader(QXcbConnection *connection); -#ifdef XCB_POLL_FOR_QUEUED_EVENT void run(); -#endif QXcbEventArray *lock(); void unlock(); + bool startThread(); + signals: void eventPending(); @@ -299,6 +296,9 @@ private: QMutex m_mutex; QXcbEventArray m_events; QXcbConnection *m_connection; + + typedef xcb_generic_event_t * (*XcbPollForQueuedEventFunctionPointer)(xcb_connection_t *c); + XcbPollForQueuedEventFunctionPointer m_xcb_poll_for_queued_event; }; class QAbstractEventDispatcher; diff --git a/src/plugins/platforms/xcb/xcb.pro b/src/plugins/platforms/xcb/xcb.pro index 34f7c74675..8a3e9e8e5e 100644 --- a/src/plugins/platforms/xcb/xcb.pro +++ b/src/plugins/platforms/xcb/xcb.pro @@ -40,9 +40,7 @@ HEADERS = \ qxcbimage.h \ qxlibconvenience.h -contains(QT_CONFIG, xcb-poll-for-queued-event) { - DEFINES += XCB_POLL_FOR_QUEUED_EVENT -} +LIBS += -ldl # needed by GLX, Xcursor, XLookupString, ... contains(QT_CONFIG, xcb-xlib) { |