diff --git a/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.cpp b/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.cpp deleted file mode 100644 index 3b244cc5e5..0000000000 --- a/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.cpp +++ /dev/null @@ -1,64 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies). -** Contact: http://www.qt-project.org/legal -** -** This file is part of the config.tests of the Qt Toolkit. -** -** $QT_BEGIN_LICENSE:LGPL$ -** Commercial License Usage -** Licensees holding valid commercial Qt licenses may use this file in -** accordance with the commercial license agreement provided with the -** Software or, alternatively, in accordance with the terms contained in -** a written agreement between you and Digia. For licensing terms and -** conditions see http://qt.digia.com/licensing. For further information -** use the contact form at http://qt.digia.com/contact-us. -** -** GNU Lesser General Public License Usage -** Alternatively, this file may be used under the terms of the GNU Lesser -** General Public License version 2.1 as published by the Free Software -** Foundation and appearing in the file LICENSE.LGPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU Lesser General Public License version 2.1 requirements -** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. -** -** In addition, as a special exception, Digia gives you certain additional -** rights. These rights are described in the Digia Qt LGPL Exception -** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. -** -** GNU General Public License Usage -** Alternatively, this file may be used under the terms of the GNU -** General Public License version 3.0 as published by the Free Software -** Foundation and appearing in the file LICENSE.GPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU General Public License version 3.0 requirements will be -** met: http://www.gnu.org/copyleft/gpl.html. -** -** -** $QT_END_LICENSE$ -** -****************************************************************************/ - -#include - -// FIXME This workaround can be removed for xcb-icccm > 3.8 -#define class class_name -#include -#undef class - -#include -#include -#include -#include -#include - -int main(int, char **) -{ - int primaryScreen = 0; - - xcb_connection_t *connection = xcb_connect("", &primaryScreen); - - xcb_generic_event_t *event = xcb_poll_for_queued_event(connection); - - return 0; -} diff --git a/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.pro b/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.pro deleted file mode 100644 index 6075c55c49..0000000000 --- a/config.tests/qpa/xcb-poll-for-queued-event/xcb-poll-for-queued-event.pro +++ /dev/null @@ -1,5 +0,0 @@ -SOURCES = xcb-poll-for-queued-event.cpp -CONFIG -= qt - -LIBS += -lxcb -lxcb-image -lxcb-keysyms -lxcb-icccm -lxcb-sync -lxcb-xfixes - diff --git a/configure b/configure index 4a4b48b1aa..97479f6432 100755 --- a/configure +++ b/configure @@ -803,7 +803,6 @@ CFG_XINPUT=runtime CFG_XKB=auto CFG_XCB=auto CFG_XCB_GLX=no -CFG_XCB_LIMITED=yes CFG_EGLFS=auto CFG_DIRECTFB=auto CFG_LINUXFB=auto @@ -4815,11 +4814,6 @@ if [ "$CFG_XCB" != "no" ]; then QT_CONFIG="$QT_CONFIG xcb-glx" fi - if compileTest qpa/xcb-poll-for-queued-event "xcb-poll-for-queued-event" $QMAKE_CFLAGS_XCB $QMAKE_LIBS_XCB; then - CFG_XCB_LIMITED=no - QT_CONFIG="$QT_CONFIG xcb-poll-for-queued-event" - fi - if compileTest qpa/xcb-xlib "xcb-xlib" $QMAKE_CFLAGS_XCB $QMAKE_LIBS_XCB; then QT_CONFIG="$QT_CONFIG xcb-xlib" fi @@ -6308,11 +6302,7 @@ if [ "$BUILD_ON_MAC" = "yes" ]; then fi echo "libICU support ......... $CFG_ICU" echo "PCRE support ........... $CFG_PCRE" -if [ "$CFG_XCB_LIMITED" = "yes" ] && [ "$CFG_XCB" = "yes" ]; then - echo "Xcb support ............ limited (old version)" -else - echo "Xcb support ............ $CFG_XCB" -fi +echo "Xcb support ............ $CFG_XCB" echo "Xrender support ........ $CFG_XRENDER" if [ "$XPLATFORM_MAEMO" = "yes" ] && [ "$CFG_XCB" = "yes" ]; then echo "XInput2 support ........ $CFG_XINPUT2" 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 #include +#include #include #include #include @@ -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) {